Update On Fri Oct 11 20:50:18 CEST 2024

This commit is contained in:
github-action[bot] 2024-10-11 20:50:19 +02:00
parent dc6f9cd8a7
commit 486b19e74e
4056 changed files with 21469 additions and 43499 deletions

View file

@ -22,4 +22,4 @@
# changes to stick? As of bug 928195, this shouldn't be necessary! Please
# don't change CLOBBER for WebIDL changes any more.
Modified build files in third_party/libwebrtc - Bug 1918268 - Vendor libwebrtc from 759f8d80f0
Bug 1921707 - modified build files in third_party/libwebrtc and third_party/abseil-cpp

4
Cargo.lock generated
View file

@ -6993,9 +6993,9 @@ dependencies = [
[[package]]
name = "webrtc-sdp"
version = "0.3.11"
version = "0.3.13"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c7351fba122c7f6566779efdef49d2213e842f69fa1c654eef1fd9301f425064"
checksum = "a87d58624aae43577604ea137de9dcaf92793eccc4d816efad482001c2e055ca"
dependencies = [
"log",
"url",

View file

@ -522,6 +522,7 @@ static const char kEventTypeNames[][40] = {
"live region added", // EVENT_LIVE_REGION_ADDED
"live region removed", // EVENT_LIVE_REGION_REMOVED
"inner reorder", // EVENT_INNER_REORDER
"live region changed", // EVENT_LIVE_REGION_CHANGED
};
#endif

View file

@ -213,10 +213,15 @@ interface nsIAccessibleEvent : nsISupports
*/
const unsigned long EVENT_INNER_REORDER = 0x0028;
/**
* A live region's contents has changed. Mac Only.
*/
const unsigned long EVENT_LIVE_REGION_CHANGED = 0x0029;
/**
* Help make sure event map does not get out-of-line.
*/
const unsigned long EVENT_LAST_ENTRY = 0x0029;
const unsigned long EVENT_LAST_ENTRY = 0x002a;
/**
* The type of event, based on the enumerated event values

View file

@ -54,6 +54,8 @@ class AccessibleWrap : public LocalAccessible {
virtual nsresult HandleAccEvent(AccEvent* aEvent) override;
static bool IsLiveRegion(nsIContent* aContent);
protected:
friend class xpcAccessibleMacInterface;

View file

@ -35,34 +35,11 @@ AccessibleWrap::AccessibleWrap(nsIContent* aContent, DocAccessible* aDoc)
: LocalAccessible(aContent, aDoc),
mNativeObject(nil),
mNativeInited(false) {
if (aContent && aContent->IsElement() && aDoc) {
if (aContent && aDoc && IsLiveRegion(aContent)) {
// Check if this accessible is a live region and queue it
// it for dispatching an event after it has been inserted.
DocAccessibleWrap* doc = static_cast<DocAccessibleWrap*>(aDoc);
static const dom::Element::AttrValuesArray sLiveRegionValues[] = {
nsGkAtoms::OFF, nsGkAtoms::polite, nsGkAtoms::assertive, nullptr};
int32_t attrValue = nsAccUtils::FindARIAAttrValueIn(
aContent->AsElement(), nsGkAtoms::aria_live, sLiveRegionValues,
eIgnoreCase);
if (attrValue == 0) {
// aria-live is "off", do nothing.
} else if (attrValue > 0) {
// aria-live attribute is polite or assertive. It's live!
doc->QueueNewLiveRegion(this);
} else if (const nsRoleMapEntry* roleMap =
aria::GetRoleMap(aContent->AsElement())) {
// aria role defines it as a live region. It's live!
if (roleMap->liveAttRule == ePoliteLiveAttr ||
roleMap->liveAttRule == eAssertiveLiveAttr) {
doc->QueueNewLiveRegion(this);
}
} else if (nsStaticAtom* value = GetAccService()->MarkupAttribute(
aContent, nsGkAtoms::aria_live)) {
// HTML element defines it as a live region. It's live!
if (value == nsGkAtoms::polite || value == nsGkAtoms::assertive) {
doc->QueueNewLiveRegion(this);
}
}
doc->QueueNewLiveRegion(this);
}
}
@ -167,11 +144,58 @@ nsresult AccessibleWrap::HandleAccEvent(AccEvent* aEvent) {
doc->ProcessNewLiveRegions();
}
if ((eventType == nsIAccessibleEvent::EVENT_TEXT_INSERTED ||
eventType == nsIAccessibleEvent::EVENT_TEXT_REMOVED ||
eventType == nsIAccessibleEvent::EVENT_NAME_CHANGE) &&
!aEvent->FromUserInput()) {
for (LocalAccessible* container = aEvent->GetAccessible(); container;
container = container->LocalParent()) {
if (container->HasOwnContent() && IsLiveRegion(container->GetContent())) {
// We rely on EventQueue::CoalesceEvents to remove duplicates
Document()->FireDelayedEvent(
nsIAccessibleEvent::EVENT_LIVE_REGION_CHANGED, container);
}
}
}
return NS_OK;
NS_OBJC_END_TRY_BLOCK_RETURN(NS_ERROR_FAILURE);
}
bool AccessibleWrap::IsLiveRegion(nsIContent* aContent) {
if (!aContent || !aContent->IsElement()) {
return false;
}
static const dom::Element::AttrValuesArray sLiveRegionValues[] = {
nsGkAtoms::OFF, nsGkAtoms::polite, nsGkAtoms::assertive, nullptr};
int32_t attrValue = nsAccUtils::FindARIAAttrValueIn(
aContent->AsElement(), nsGkAtoms::aria_live, sLiveRegionValues,
eIgnoreCase);
if (attrValue == 0) {
// aria-live is "off", do nothing.
} else if (attrValue > 0) {
// aria-live attribute is polite or assertive. It's live!
return true;
} else if (const nsRoleMapEntry* roleMap =
aria::GetRoleMap(aContent->AsElement())) {
// aria role defines it as a live region. It's live!
if (roleMap->liveAttRule == ePoliteLiveAttr ||
roleMap->liveAttRule == eAssertiveLiveAttr) {
return true;
}
} else if (nsStaticAtom* value = GetAccService()->MarkupAttribute(
aContent, nsGkAtoms::aria_live)) {
// HTML element defines it as a live region. It's live!
if (value == nsGkAtoms::polite || value == nsGkAtoms::assertive) {
return true;
}
}
return false;
}
////////////////////////////////////////////////////////////////////////////////
// AccessibleWrap protected

View file

@ -101,5 +101,10 @@ void DocAccessibleWrap::ProcessNewLiveRegions() {
void DocAccessibleWrap::DoInitialUpdate() {
DocAccessible::DoInitialUpdate();
if (IsLiveRegion(mDocumentNode->GetBodyElement())) {
// Check if this doc's body element is a live region
QueueNewLiveRegion(this);
}
ProcessNewLiveRegions();
}

View file

@ -99,6 +99,7 @@ void PlatformEvent(Accessible* aTarget, uint32_t aEventType) {
aEventType != nsIAccessibleEvent::EVENT_REORDER &&
aEventType != nsIAccessibleEvent::EVENT_LIVE_REGION_ADDED &&
aEventType != nsIAccessibleEvent::EVENT_LIVE_REGION_REMOVED &&
aEventType != nsIAccessibleEvent::EVENT_LIVE_REGION_CHANGED &&
aEventType != nsIAccessibleEvent::EVENT_NAME_CHANGE &&
aEventType != nsIAccessibleEvent::EVENT_OBJECT_ATTRIBUTE_CHANGED) {
return;

View file

@ -43,7 +43,6 @@ using namespace mozilla::a11y;
@interface mozAccessible ()
- (BOOL)providesLabelNotTitle;
- (void)maybePostLiveRegionChanged;
- (void)maybePostA11yUtilNotification;
@end
@ -869,17 +868,6 @@ struct RoleDescrComparator {
return NO;
}
- (void)maybePostLiveRegionChanged {
id<MOXAccessible> liveRegion =
[self moxFindAncestor:^BOOL(id<MOXAccessible> moxAcc, BOOL* stop) {
return [moxAcc moxIsLiveRegion];
}];
if (liveRegion) {
[liveRegion moxPostNotification:@"AXLiveRegionChanged"];
}
}
- (void)maybePostA11yUtilNotification {
MOZ_ASSERT(mGeckoAccessible);
// Sometimes we use a special live region to make announcements to the user.
@ -1004,16 +992,15 @@ struct RoleDescrComparator {
case nsIAccessibleEvent::EVENT_LIVE_REGION_REMOVED:
mIsLiveRegion = false;
break;
case nsIAccessibleEvent::EVENT_REORDER:
[self maybePostLiveRegionChanged];
break;
case nsIAccessibleEvent::EVENT_NAME_CHANGE: {
case nsIAccessibleEvent::EVENT_NAME_CHANGE:
if (![self providesLabelNotTitle]) {
[self moxPostNotification:NSAccessibilityTitleChangedNotification];
}
[self maybePostLiveRegionChanged];
break;
}
case nsIAccessibleEvent::EVENT_LIVE_REGION_CHANGED:
MOZ_ASSERT(mIsLiveRegion);
[self moxPostNotification:@"AXLiveRegionChanged"];
break;
}
}

View file

@ -161,5 +161,19 @@ addAccessibleTask(
});
await liveRegionChanged;
ok(true, "changed aria-label");
liveRegionChanged = waitForMacEvent("AXLiveRegionChanged", "live");
await SpecialPowers.spawn(browser, [], () => {
content.document.getElementById("live").firstChild.data = "The hour is ";
});
await liveRegionChanged;
ok(true, "changed text leaf contents");
liveRegionChanged = waitForMacEvent("AXLiveRegionChanged", "live");
await SpecialPowers.spawn(browser, [], () => {
content.document.getElementById("live").firstChild.data = "";
});
await liveRegionChanged;
ok(true, "delete text leaf contents");
}
);

View file

@ -53,5 +53,6 @@ static const uint32_t gWinEventMap[] = {
kEVENT_WIN_UNKNOWN, // nsIAccessibleEvent::EVENT_LIVE_REGION_ADDED
kEVENT_WIN_UNKNOWN, // nsIAccessibleEvent::EVENT_LIVE_REGION_REMOVED
kEVENT_WIN_UNKNOWN, // nsIAccessibleEvent::EVENT_INNER_REORDER
kEVENT_WIN_UNKNOWN, // nsIAccessibleEvent::EVENT_LIVE_REGION_CHANGED
// clang-format on
};

View file

@ -499,6 +499,10 @@ pref("browser.urlbar.quicksuggest.enabled", false);
// Whether Suggest should be hidden in the settings UI even when enabled.
pref("browser.urlbar.quicksuggest.hideSettingsUI", false);
// Ranking mode of QuickSuggest. Currently used for relevance ranking
// experimentation. It can be any of "default", "interest", and "random".
pref("browser.urlbar.quicksuggest.rankingMode", "default");
// Whether Firefox Suggest will use the new Rust backend instead of the original
// JS backend.
pref("browser.urlbar.quicksuggest.rustEnabled", true);

View file

@ -5829,7 +5829,7 @@ function warnAboutClosingWindow() {
if (!isPBWindow && !toolbar.visible) {
return gBrowser.warnAboutClosingTabs(
gBrowser.visibleTabs.length,
gBrowser.openTabCount,
gBrowser.closingTabsEnum.ALL
);
}
@ -5869,7 +5869,7 @@ function warnAboutClosingWindow() {
return (
isPBWindow ||
gBrowser.warnAboutClosingTabs(
gBrowser.visibleTabs.length,
gBrowser.openTabCount,
gBrowser.closingTabsEnum.ALL
)
);
@ -5894,7 +5894,7 @@ function warnAboutClosingWindow() {
AppConstants.platform != "macosx" ||
isPBWindow ||
gBrowser.warnAboutClosingTabs(
gBrowser.visibleTabs.length,
gBrowser.openTabCount,
gBrowser.closingTabsEnum.ALL
)
);

View file

@ -7,7 +7,7 @@
<!-- Menu -->
<toolbar type="menubar" id="toolbar-menubar"
class="browser-toolbar chromeclass-menubar browser-titlebar titlebar-color"
class="browser-toolbar chromeclass-menubar browser-titlebar"
customizable="true"
mode="icons"
context="toolbar-context-menu">
@ -21,7 +21,7 @@
</toolbar>
<toolbar id="TabsToolbar"
class="browser-toolbar browser-titlebar titlebar-color"
class="browser-toolbar browser-titlebar"
fullscreentoolbar="true"
customizable="true"
customizationtarget="TabsToolbar-customization-target"

View file

@ -19,6 +19,7 @@ add_task(async function () {
let visible = gBrowser.visibleTabs;
is(visible.length, 3, "3 tabs should be visible");
is(gBrowser.openTabCount, 4, "number of tabs to be considered open (step 1)");
is(visible[0], pinned, "the pinned tab is first");
is(visible[1], origTab, "original tab is next");
is(visible[2], testTab, "last created tab is next to last");
@ -31,6 +32,7 @@ add_task(async function () {
);
gBrowser.showOnlyTheseTabs([testTab]);
is(gBrowser.visibleTabs.length, 3, "all 3 tabs are still visible");
is(gBrowser.openTabCount, 4, "number of tabs to be considered open (step 2)");
info("Select the test tab and only show that (and pinned)");
gBrowser.selectedTab = testTab;
@ -41,6 +43,7 @@ add_task(async function () {
is(visible[0], pinned, "first is pinned");
is(visible[1], testTab, "next is the test tab");
is(gBrowser.tabs.length, 4, "4 tabs should still be open");
is(gBrowser.openTabCount, 4, "number of tabs to be considered open (step 3)");
gBrowser.selectTabAtIndex(1);
is(gBrowser.selectedTab, testTab, "second tab is the test tab");
@ -92,6 +95,7 @@ add_task(async function () {
info("Try showing all tabs except for the Firefox View tab");
gBrowser.showOnlyTheseTabs(Array.from(gBrowser.tabs.slice(0, 3)));
is(gBrowser.visibleTabs.length, 3, "all 3 tabs are visible again");
is(gBrowser.openTabCount, 4, "number of tabs to be considered open (step 4)");
info(
"Select the pinned tab and show the testTab to make sure selection updates"
@ -103,10 +107,12 @@ add_task(async function () {
gBrowser.removeTab(pinned);
is(gBrowser.selectedTab, testTab, "making sure origTab was skipped");
is(gBrowser.visibleTabs.length, 1, "only testTab is there");
is(gBrowser.openTabCount, 3, "number of tabs to be considered open (step 5)");
info("Only show one of the non-pinned tabs (but testTab is selected)");
gBrowser.showOnlyTheseTabs([origTab]);
is(gBrowser.visibleTabs.length, 2, "got 2 tabs");
is(gBrowser.openTabCount, 3, "number of tabs to be considered open (step 6)");
info("Now really only show one of the tabs");
gBrowser.showOnlyTheseTabs([testTab]);
@ -114,6 +120,7 @@ add_task(async function () {
is(visible.length, 1, "only the original tab is visible");
is(visible[0], testTab, "it's the original tab");
is(gBrowser.tabs.length, 3, "still have 3 open tabs");
is(gBrowser.openTabCount, 3, "number of tabs to be considered open (step 7)");
info("Close the selectable hidden tab");
gBrowser.removeTab(firefoxViewTab);
@ -127,6 +134,7 @@ add_task(async function () {
gBrowser.removeTab(testTab);
is(gBrowser.visibleTabs.length, 1, "a new visible tab was opened");
is(gBrowser.tabs.length, 2, "we have two tabs in total");
is(gBrowser.openTabCount, 2, "number of tabs to be considered open (step 8)");
ok(origTab.hidden, "original tab is still hidden");
ok(!origTab.selected, "original tab is not selected");
gBrowser.removeTab(origTab);

View file

@ -1,5 +1,13 @@
"use strict";
const { SessionStoreTestUtils } = ChromeUtils.importESModule(
"resource://testing-common/SessionStoreTestUtils.sys.mjs"
);
const { NonPrivateTabs } = ChromeUtils.importESModule(
"resource:///modules/OpenTabs.sys.mjs"
);
// Testing that when the user opens the add tab menu and clicks menu items
// the correct context id is opened
@ -11,6 +19,17 @@ function findContextPopup() {
return document.querySelector("#new-tab-button-popup");
}
add_setup(function () {
SessionStoreTestUtils.init(this, window);
registerCleanupFunction(async () => {
await SpecialPowers.popPrefEnv();
while (gBrowser.tabs.length > 1) {
BrowserTestUtils.removeTab(gBrowser.tabs.at(-1));
}
NonPrivateTabs.stop();
});
});
add_task(async function test_containers_no_left_click() {
await SpecialPowers.pushPrefEnv({
set: [
@ -246,3 +265,58 @@ add_task(async function test_vertical_tabs_right_click_new_tab_button() {
await SpecialPowers.popPrefEnv();
});
add_task(async function test_vertical_tabs_right_click_other_new_tab_button() {
await SpecialPowers.pushPrefEnv({
set: [["sidebar.verticalTabs", true]],
});
const sidebar = window.document.querySelector("sidebar-main");
await TestUtils.waitForCondition(
() => sidebar.toolButtons,
"Tool buttons are shown."
);
const numTabs = 50;
const winData = {
tabs: Array.from({ length: numTabs }, (_, i) => ({
entries: [
{
url: `data:,Tab${i}`,
triggeringPrincipal_base64: E10SUtils.SERIALIZED_SYSTEMPRINCIPAL,
},
],
})),
selected: numTabs,
};
const browserState = { windows: [winData] };
// use Session restore to batch-open tabs
info(`Restoring to browserState: ${JSON.stringify(browserState, null, 2)}`);
await SessionStoreTestUtils.promiseBrowserState(browserState);
info("Windows and tabs opened, waiting for readyWindowsPromise");
await NonPrivateTabs.readyWindowsPromise;
info("readyWindowsPromise resolved");
const newTabButton = sidebar.querySelector("#vertical-tabs-newtab-button");
let popup = findPopup();
ok(popup, "new tab should have a popup");
// Test context menu
let contextMenu = findContextPopup();
is(contextMenu.state, "closed", "Context menu is initally closed.");
// Right click
let popupshownContextmenu = BrowserTestUtils.waitForEvent(
contextMenu,
"popupshown"
);
EventUtils.synthesizeMouseAtCenter(newTabButton, { type: "contextmenu" });
await popupshownContextmenu;
is(contextMenu.state, "open", "Context menu is open.");
let contextIdItems = contextMenu.querySelectorAll("menuitem");
// 4 + default + manage containers
is(contextIdItems.length, 6, "Has 6 menu items");
contextMenu.hidePopup();
await SpecialPowers.popPrefEnv();
});

View file

@ -73,7 +73,7 @@ add_task(async function () {
);
let tab3 = await BrowserTestUtils.openNewForegroundTab(
gBrowser,
"http://test1.example.org/MochiKit/"
"http://test1.example.org/Http2Server/"
);
// test simple queries
@ -104,7 +104,7 @@ add_task(async function () {
);
browser.test.assertEq(
tabs[2].url,
"http://test1.example.org/MochiKit/",
"http://test1.example.org/Http2Server/",
"tab 2 url correct"
);
@ -127,14 +127,14 @@ add_task(async function () {
background: function () {
browser.tabs.query(
{
url: "http://*/MochiKit*",
url: "http://*/Http2Server*",
},
function (tabs) {
browser.test.assertEq(tabs.length, 1, "should have one tab");
browser.test.assertEq(
tabs[0].url,
"http://test1.example.org/MochiKit/",
"http://test1.example.org/Http2Server/",
"tab 0 url correct"
);
@ -157,7 +157,7 @@ add_task(async function () {
background: function () {
browser.tabs.query(
{
url: ["http://*/MochiKit*", "http://*.com/*"],
url: ["http://*/Http2Server*", "http://*.com/*"],
},
function (tabs) {
browser.test.assertEq(tabs.length, 2, "should have two tabs");
@ -171,7 +171,7 @@ add_task(async function () {
);
browser.test.assertEq(
tabs[1].url,
"http://test1.example.org/MochiKit/",
"http://test1.example.org/Http2Server/",
"tab 1 url correct"
);
@ -231,7 +231,7 @@ add_task(async function () {
);
browser.test.assertEq(
tabs[2].title,
"mochitest index /MochiKit/",
"mochitest index /Http2Server/",
"tab 2 title correct"
);

View file

@ -217,7 +217,7 @@ export class _DSCard extends React.PureComponent {
doesLinkTopicMatchSelectedTopic() {
// Edge case for clicking on a card when topic selections have not be set
if (this.props.selectedTopics === "") {
if (!this.props.selectedTopics) {
return "not-set";
}

View file

@ -2956,7 +2956,7 @@ class _DSCard extends (external_React_default()).PureComponent {
}
doesLinkTopicMatchSelectedTopic() {
// Edge case for clicking on a card when topic selections have not be set
if (this.props.selectedTopics === "") {
if (!this.props.selectedTopics) {
return "not-set";
}

View file

@ -57,7 +57,7 @@ export class ProfilesParent extends JSWindowActorParent {
let name = SelectableProfileService.currentProfile.name;
let windowCount = lazy.EveryWindow.readyWindows.length;
let tabCount = lazy.EveryWindow.readyWindows
.flatMap(win => win.gBrowser.visibleTabs.length)
.flatMap(win => win.gBrowser.openTabCount)
.reduce((total, current) => total + current);
let loginCount = (await lazy.LoginHelper.getAllUserFacingLogins())
.length;
@ -88,6 +88,11 @@ export class ProfilesParent extends JSWindowActorParent {
loginCount,
};
}
case "Profiles:UpdateProfileAvatar": {
let profileObj = message.data;
SelectableProfileService.currentProfile.avatar = profileObj.avatar;
break;
}
}
return null;
}

View file

@ -110,7 +110,7 @@ export class SelectableProfile {
* @param {string} aAvatar Name of the avatar
*/
set avatar(aAvatar) {
this.avatar = aAvatar;
this.#avatar = aAvatar;
this.saveUpdatesToDB();
}
@ -154,12 +154,14 @@ export class SelectableProfile {
}
toObject() {
return {
let profileObj = {
id: this.id,
path: this.#path,
name: this.name,
avatar: this.avatar,
...this.theme,
};
return profileObj;
}
}

View file

@ -3,5 +3,5 @@
- file, You can obtain one at https://mozilla.org/MPL/2.0/. -->
<svg width="80" height="80" viewBox="0 0 80 80" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M4.67475e-07 40C3.96467e-07 62.0914 17.9086 80 40 80C62.0914 80 80 62.0914 80 40C80 17.9086 62.0914 5.44299e-08 40 1.21573e-07C17.9086 1.88715e-07 5.38483e-07 17.9086 4.67475e-07 40Z" fill="context-fill"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M38.8884 24.7634C38.8884 24.7634 38.8884 24.7634 38.8884 24.7634L35.2844 33.8173C35.0881 34.3104 34.6255 34.6466 34.0958 34.6809L24.3718 35.3109C23.2927 35.3807 22.8532 36.7332 23.6851 37.4238L31.1823 43.6489C31.5907 43.988 31.7674 44.5319 31.6363 45.0463L29.2303 54.4892C29.2303 54.4892 29.2303 54.4892 29.2303 54.4892C28.9634 55.537 30.1141 56.3732 31.0282 55.7955C31.0282 55.7955 31.0282 55.7955 31.0282 55.7955L39.2652 50.5885C39.7139 50.3048 40.2859 50.3048 40.7346 50.5885L48.9715 55.7955C48.9716 55.7955 48.9715 55.7955 48.9715 55.7955C49.885 56.3727 51.0356 55.5378 50.7685 54.4892L48.3625 45.0463C48.2314 44.5319 48.4081 43.988 48.8165 43.6489L56.3135 37.4239C57.1454 36.7334 56.7063 35.3807 55.6272 35.3109L45.903 34.6809C45.3733 34.6466 44.9107 34.3104 44.7144 33.8173L41.1104 24.7633C40.7113 23.7598 39.2888 23.758 38.8884 24.7634ZM43.6654 23.7462C42.3463 20.4301 37.653 20.4318 36.3334 23.7461L33.0508 31.9928L24.1942 32.5666C24.1942 32.5666 24.1941 32.5666 24.1942 32.5666C20.6334 32.797 19.1826 37.2604 21.9287 39.5398L28.7569 45.2094L26.5655 53.8103C25.6844 57.2684 29.4816 60.0263 32.4975 58.1201L39.9999 53.3775L47.5022 58.12C50.5188 60.0267 54.3142 57.2677 53.4333 53.8103L51.2419 45.2094L58.0701 39.5398C58.0701 39.5398 58.0702 39.5397 58.0701 39.5398C60.8159 37.2603 59.3655 32.797 55.8048 32.5666C55.8049 32.5666 55.8047 32.5666 55.8048 32.5666L46.948 31.9928L43.6654 23.7462C43.6655 23.7464 43.6654 23.7461 43.6654 23.7462Z" fill="context-fill"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M38.8884 24.7634C38.8884 24.7634 38.8884 24.7634 38.8884 24.7634L35.2844 33.8173C35.0881 34.3104 34.6255 34.6466 34.0958 34.6809L24.3718 35.3109C23.2927 35.3807 22.8532 36.7332 23.6851 37.4238L31.1823 43.6489C31.5907 43.988 31.7674 44.5319 31.6363 45.0463L29.2303 54.4892C29.2303 54.4892 29.2303 54.4892 29.2303 54.4892C28.9634 55.537 30.1141 56.3732 31.0282 55.7955C31.0282 55.7955 31.0282 55.7955 31.0282 55.7955L39.2652 50.5885C39.7139 50.3048 40.2859 50.3048 40.7346 50.5885L48.9715 55.7955C48.9716 55.7955 48.9715 55.7955 48.9715 55.7955C49.885 56.3727 51.0356 55.5378 50.7685 54.4892L48.3625 45.0463C48.2314 44.5319 48.4081 43.988 48.8165 43.6489L56.3135 37.4239C57.1454 36.7334 56.7063 35.3807 55.6272 35.3109L45.903 34.6809C45.3733 34.6466 44.9107 34.3104 44.7144 33.8173L41.1104 24.7633C40.7113 23.7598 39.2888 23.758 38.8884 24.7634ZM43.6654 23.7462C42.3463 20.4301 37.653 20.4318 36.3334 23.7461L33.0508 31.9928L24.1942 32.5666C24.1942 32.5666 24.1941 32.5666 24.1942 32.5666C20.6334 32.797 19.1826 37.2604 21.9287 39.5398L28.7569 45.2094L26.5655 53.8103C25.6844 57.2684 29.4816 60.0263 32.4975 58.1201L39.9999 53.3775L47.5022 58.12C50.5188 60.0267 54.3142 57.2677 53.4333 53.8103L51.2419 45.2094L58.0701 39.5398C58.0701 39.5398 58.0702 39.5397 58.0701 39.5398C60.8159 37.2603 59.3655 32.797 55.8048 32.5666C55.8049 32.5666 55.8047 32.5666 55.8048 32.5666L46.948 31.9928L43.6654 23.7462C43.6655 23.7464 43.6654 23.7461 43.6654 23.7462Z" fill="context-stroke"/>
</svg>

Before

Width:  |  Height:  |  Size: 2 KiB

After

Width:  |  Height:  |  Size: 2 KiB

Before After
Before After

View file

@ -0,0 +1,43 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
:host {
--avatar-size: 40px;
--avatar-img-size: 20px;
}
.avatar {
display: flex;
align-items: center;
justify-content: center;
appearance: none;
background-color: transparent;
padding: 0;
outline-offset: var(--focus-outline-offset);
box-sizing: border-box;
width: var(--avatar-size);
height: var(--avatar-size);
border-radius: var(--border-radius-circle);
border: 1px solid var(--border-color-interactive);
> img {
width: var(--avatar-img-size);
height: var(--avatar-img-size);
-moz-context-properties: fill, stroke;
fill: transparent;
stroke: currentColor;
}
&:hover {
background-color: var(--button-background-color-hover);
}
&:focus-visible {
outline: var(--focus-outline);
}
}
:host([selected]) .avatar {
border: var(--focus-outline);
}

View file

@ -0,0 +1,30 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { MozLitElement } from "chrome://global/content/lit-utils.mjs";
import { html } from "chrome://global/content/vendor/lit.all.mjs";
/**
* Element used for selecting an avatar
*/
export class Avatar extends MozLitElement {
static properties = {
value: { type: String },
selected: { type: Boolean, reflect: true },
};
render() {
return html`<link
rel="stylesheet"
href="chrome://browser/content/profiles/avatar.css"
/>
<button type="button" class="avatar">
<img
src="chrome://browser/content/profiles/assets/48_${this.value}.svg"
/>
</button>`;
}
}
customElements.define("profiles-avatar", Avatar);

View file

@ -2,6 +2,11 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
:host {
--header-avatar-size: 80px;
--header-avatar-img-size: 40px;
}
html,
body {
width: 100%;
@ -34,6 +39,14 @@ edit-profile-card {
gap: var(--space-medium);
}
#header-avatar {
-moz-context-properties: fill, stroke;
width: var(--header-avatar-size);
height: var(--header-avatar-size);
border-radius: var(--border-radius-circle);
}
#profile-name-area {
display: flex;
flex-direction: column;
@ -96,12 +109,4 @@ edit-profile-card {
display: flex;
flex-wrap: wrap;
gap: var(--space-xlarge);
/* TODO: bug 1886007 will implement the avatars */
> .avatar {
width: 40px;
height: 40px;
border: 1px solid;
border-radius: 20px;
}
}

View file

@ -13,6 +13,8 @@ import "chrome://global/content/elements/moz-card.mjs";
import "chrome://global/content/elements/moz-button.mjs";
// eslint-disable-next-line import/no-unassigned-import
import "chrome://global/content/elements/moz-button-group.mjs";
// eslint-disable-next-line import/no-unassigned-import
import "chrome://browser/content/profiles/avatar.mjs";
const SAVE_NAME_TIMEOUT = 2000;
const SAVED_MESSAGE_TIMEOUT = 5000;
@ -31,6 +33,8 @@ export class EditProfileCard extends MozLitElement {
nameInput: "#profile-name",
errorMessage: "#error-message",
savedMessage: "#saved-message",
avatars: { all: "profiles-avatar" },
headerAvatar: "#header-avatar",
};
connectedCallback() {
@ -62,6 +66,18 @@ export class EditProfileCard extends MozLitElement {
};
}
updated() {
super.updated();
if (!this.profile) {
return;
}
let { themeFg, themeBg } = this.profile;
this.headerAvatar.style.fill = themeBg;
this.headerAvatar.style.stroke = themeFg;
}
updateName() {
this.savedMessage.parentElement.hidden = false;
if (this.saveMessageTimeoutId) {
@ -70,6 +86,7 @@ export class EditProfileCard extends MozLitElement {
this.saveMessageTimeoutId = setTimeout(() => {
this.savedMessage.parentElement.hidden = true;
}, SAVED_MESSAGE_TIMEOUT);
let newName = this.nameInput.value.trim();
if (!newName) {
return;
@ -79,6 +96,16 @@ export class EditProfileCard extends MozLitElement {
RPMSendAsyncMessage("Profiles:UpdateProfileName", this.profile);
}
async updateAvatar(newAvatar) {
if (newAvatar === this.profile.avatar) {
return;
}
this.profile.avatar = newAvatar;
RPMSendAsyncMessage("Profiles:UpdateProfileAvatar", this.profile);
this.requestUpdate();
}
isDuplicateName(newName) {
return !!this.profiles.find(
p => p.id !== this.profile.id && p.name === newName
@ -166,10 +193,27 @@ export class EditProfileCard extends MozLitElement {
}
avatarsTemplate() {
// TODO: bug 1886007 will implement the avatars
let avatars = ["star", "flower", "briefcase", "book", "heart", "shopping"];
let avatars = ["book", "briefcase", "flower", "heart", "shopping", "star"];
return avatars.map(s => html`<div class="avatar">${s}</div>`);
return avatars.map(
avatar =>
html`<profiles-avatar
@click=${this.handleAvatarClick}
value=${avatar}
?selected=${avatar === this.profile.avatar}
></profiles-avatar>`
);
}
handleAvatarClick(event) {
for (let a of this.avatars) {
a.selected = false;
}
let selectedAvatar = event.target;
selectedAvatar.selected = true;
this.updateAvatar(selectedAvatar.value);
}
onDeleteClick() {
@ -191,7 +235,11 @@ export class EditProfileCard extends MozLitElement {
/>
<moz-card
><div id="edit-profile-card">
<img width="80" height="80" src="${this.profile.avatar}" />
<img
id="header-avatar"
src="chrome://browser/content/profiles/assets/80_${this.profile
.avatar}.svg"
/>
<div id="profile-content">
<h1 data-l10n-id="edit-profile-page-header"></h1>

View file

@ -4,6 +4,10 @@
@import url("chrome://global/skin/design-system/text-and-typography.css");
:host {
--avatar-size: 80px;
}
.profile-card {
height: 185px;
width: 200px;
@ -49,6 +53,7 @@
}
.profile-background-container {
position: relative;
width: 200px;
height: 136px;
@ -58,6 +63,7 @@
}
.profile-background-image {
position: absolute;
width: 100%;
height: 100%;
background-image: url("chrome://global/skin/icons/plus.svg");
@ -70,6 +76,17 @@
border-radius: var(--border-radius-medium) var(--border-radius-medium) 0 0;
}
.profile-avatar {
width: var(--avatar-size);
height: var(--avatar-size);
z-index: 1;
background-size: contain;
background-repeat: no-repeat;
background-position: center;
-moz-context-properties: fill, stroke;
}
.profile-details {
display: flex;
align-items: center;

View file

@ -22,10 +22,19 @@ export class ProfileCard extends MozLitElement {
profile: { type: SelectableProfile, reflect: true },
};
static queries = { backgroundImage: ".profile-background-image" };
static queries = {
backgroundImage: ".profile-background-image",
avatarImage: ".profile-avatar",
};
firstUpdated() {
super.firstUpdated();
this.setBackgroundImage();
this.setAvatarImage();
}
setBackgroundImage() {
this.backgroundImage.style.backgroundImage = `url("chrome://browser/content/profiles/assets/profilesBackground${
this.profile.id % 5
}.svg")`;
@ -34,6 +43,13 @@ export class ProfileCard extends MozLitElement {
this.backgroundImage.style.stroke = themeFg;
}
setAvatarImage() {
this.avatarImage.style.backgroundImage = `url("chrome://browser/content/profiles/assets/80_${this.profile.avatar}.svg")`;
let { themeFg, themeBg } = this.profile.theme;
this.avatarImage.style.fill = themeBg;
this.avatarImage.style.stroke = themeFg;
}
launchProfile(url) {
this.dispatchEvent(
new CustomEvent("LaunchProfile", {

View file

@ -3,6 +3,8 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
browser.jar:
content/browser/profiles/avatar.css (content/avatar.css)
content/browser/profiles/avatar.mjs (content/avatar.mjs)
content/browser/profiles/delete-profile-card.css (content/delete-profile-card.css)
content/browser/profiles/delete-profile-card.mjs (content/delete-profile-card.mjs)
content/browser/profiles/delete-profile.html (content/delete-profile.html)

View file

@ -199,7 +199,11 @@ export default class SidebarMain extends MozLitElement {
}
break;
case "contextmenu":
if (e.target.id != "tabs-newtab-button") {
if (
!["tabs-newtab-button", "vertical-tabs-newtab-button"].includes(
e.target.id
)
) {
this.onSidebarPopupShowing(e);
}
break;

View file

@ -37,14 +37,10 @@ var gTabsPanel = {
},
hasHiddenTabsExcludingFxView() {
const hiddenTabCount = gBrowser.tabs.length - gBrowser.visibleTabs.length;
// If there's only 1 hidden tab, check if it's Firefox View to exclude it.
// See Bug 1880138.
if (hiddenTabCount == 1) {
return !FirefoxViewHandler.tab?.hidden;
}
return hiddenTabCount > 0;
// Exclude Firefox View, see Bug 1880138.
return gBrowser.tabs.some(
tab => tab.hidden && tab != FirefoxViewHandler.tab
);
},
init() {

View file

@ -384,6 +384,18 @@
return this.tabContainer.visibleTabs;
},
/**
* Returns the number of tabs in the current window, including hidden tabs
* and tabs in collapsed groups, but excluding the Firefox View tab.
*/
get openTabCount() {
let count = this.tabs.length - this._removingTabs.size;
if (FirefoxViewHandler.tab) {
count--;
}
return count;
},
getDuplicateTabsToClose(aTab) {
// One would think that a set is better, but it would need to copy all
// the strings instead of just keeping references to the nsIURI objects,
@ -2941,11 +2953,15 @@
return t;
},
addTabGroup(color, label = "", tabs) {
addTabGroup(color = "", label = "", tabs) {
if (!tabs?.length) {
throw new Error("Cannot create tab group with zero tabs");
}
if (!color) {
color = this.tabGroupMenu.nextUnusedColor;
}
let group = document.createXULElement("tab-group", { is: "tab-group" });
group.id = `${Date.now()}-${Math.round(Math.random() * 100)}`;
group.color = color;
@ -7776,6 +7792,7 @@ var TabBarVisibility = {
update(force = false) {
let toolbar = document.getElementById("TabsToolbar");
let navbar = document.getElementById("nav-bar");
let hideTabstrip = false;
let isPopup = !window.toolbar.visible;
let isVerticalTabs = Services.prefs.getBoolPref(
@ -7793,7 +7810,7 @@ var TabBarVisibility = {
if (nonPopupWithVerticalTabs) {
// TabsInTitlebar decides if we can draw within the titlebar area.
// In vertical tabs mode, the toolbar with the horizontal tabstrip gets hidden
// and the navbar becomes a titlebar. This makie TabsInTitlebar a bit of a misnomer.
// and the navbar becomes a titlebar. This makes TabsInTitlebar a bit of a misnomer.
// We'll fix this in Bug 1921034.
hideTabstrip = true;
TabsInTitlebar.allowedBy("tabs-visible", true);
@ -7801,24 +7818,24 @@ var TabBarVisibility = {
TabsInTitlebar.allowedBy("tabs-visible", !hideTabstrip);
}
navbar.toggleAttribute("tabs-hidden", hideTabstrip);
// Should the nav-bar look and function like a titlebar?
navbar.classList.toggle(
"browser-titlebar",
TabsInTitlebar.enabled && hideTabstrip
);
if (
hideTabstrip == toolbar.collapsed &&
!force &&
this._initialUpdateDone
) {
// no further updates needed, toolbar.collapsed already matches hideTabstrip
return;
}
this._initialUpdateDone = true;
toolbar.collapsed = hideTabstrip;
let navbar = document.getElementById("nav-bar");
navbar.toggleAttribute("tabs-hidden", hideTabstrip);
// Should the nav-bar look and function like a titlebar?
navbar.classList.toggle(
"browser-titlebar",
TabsInTitlebar.enabled && hideTabstrip
);
navbar.classList.toggle("titlebar-color", hideTabstrip);
document.getElementById("menu_closeWindow").hidden = hideTabstrip;
document.l10n.setAttributes(
@ -7947,15 +7964,14 @@ var TabContextMenu = {
document.l10n.setAttributes(item, "tab-context-unnamed-group");
}
item.classList.add("menuitem-iconic");
item.setAttribute(
"image",
`data:image/svg+xml;utf8,
<svg width="32" height="32" viewBox="0 0 32 32" fill="none" xmlns="http://www.w3.org/2000/svg">
<rect width="32" height="32" rx="2" fill="${encodeURIComponent(
group.color
)}"/>
</svg>`
item.classList.add("menuitem-iconic", "tab-contextmenu-group-icon");
item.style.setProperty(
"--tab-group-color",
group.style.getPropertyValue("--tab-group-color")
);
item.style.setProperty(
"--tab-group-color-invert",
group.style.getPropertyValue("--tab-group-color-invert")
);
submenu.appendChild(item);
});
@ -8261,7 +8277,7 @@ var TabContextMenu = {
moveTabsToNewGroup() {
gBrowser.addTabGroup(
"red",
null,
"",
gBrowser.selectedTabs.includes(this.contextTab)
? gBrowser.selectedTabs

View file

@ -176,6 +176,24 @@
});
}
get nextUnusedColor() {
let usedColors = [];
gBrowser.getAllTabGroups().forEach(group => {
usedColors.push(group.color);
});
let color = MozTabbrowserTabGroupMenu.COLORS.find(
colorCode => !usedColors.includes(colorCode)
);
if (!color) {
// if all colors are used, pick one randomly
let randomIndex = Math.floor(
Math.random() * MozTabbrowserTabGroupMenu.COLORS.length
);
color = MozTabbrowserTabGroupMenu.COLORS[randomIndex];
}
return color;
}
get panel() {
return this.children[0];
}

View file

@ -60,6 +60,34 @@ add_task(async function test_getTabGroups() {
);
});
/**
* Tests that creating a group without specifying a color will select a
* unique color.
*/
add_task(async function test_tabGroupUniqueColors() {
let initialTab = BrowserTestUtils.addTab(gBrowser, "about:blank", {
skipAnimation: true,
});
let initialGroup = gBrowser.addTabGroup(null, null, [initialTab]);
let existingGroups = [initialGroup];
for (let i = 2; i <= 9; i++) {
let newTab = BrowserTestUtils.addTab(gBrowser, "about:blank", {
skipAnimation: true,
});
let newGroup = gBrowser.addTabGroup(null, null, [newTab]);
Assert.ok(
!existingGroups.find(grp => grp.color == newGroup.color),
`Group ${i} has a distinct color`
);
existingGroups.push(newGroup);
}
for (let group of existingGroups) {
await removeTabGroup(group);
}
});
add_task(async function test_tabGroupCollapseAndExpand() {
let tab1 = BrowserTestUtils.addTab(gBrowser, "about:blank");
let group = gBrowser.addTabGroup("blue", "test", [tab1]);
@ -674,9 +702,17 @@ add_task(async function test_tabGroupContextMenuMoveTabToGroupBasics() {
"group2 menu item has correct label"
);
Assert.ok(
group2Item.getAttribute("image").includes('fill="blue"'),
group2Item.style
.getPropertyValue("--tab-group-color")
.includes("--tab-group-color-blue"),
"group2 menu item chicklet has correct color"
);
Assert.ok(
group2Item.style
.getPropertyValue("--tab-group-color-invert")
.includes("--tab-group-color-blue-invert"),
"group2 menu item chicklet has correct inverted color"
);
const group1Item = submenu[2];
Assert.equal(
@ -690,9 +726,17 @@ add_task(async function test_tabGroupContextMenuMoveTabToGroupBasics() {
"group1 menu item has correct label"
);
Assert.ok(
group1Item.getAttribute("image").includes('fill="red"'),
group1Item.style
.getPropertyValue("--tab-group-color")
.includes("--tab-group-color-red"),
"group1 menu item chicklet has correct color"
);
Assert.ok(
group1Item.style
.getPropertyValue("--tab-group-color-invert")
.includes("--tab-group-color-red-invert"),
"group1 menu item chicklet has correct inverted color"
);
}
);

View file

@ -10,8 +10,11 @@ import {
const lazy = {};
ChromeUtils.defineESModuleGetters(lazy, {
ContentRelevancyManager:
"resource://gre/modules/ContentRelevancyManager.sys.mjs",
CONTEXTUAL_SERVICES_PING_TYPES:
"resource:///modules/PartnerLinkAttribution.sys.mjs",
Interest: "resource://gre/modules/RustRelevancy.sys.mjs",
MerinoClient: "resource:///modules/MerinoClient.sys.mjs",
QuickSuggest: "resource:///modules/QuickSuggest.sys.mjs",
SearchUtils: "resource://gre/modules/SearchUtils.sys.mjs",
@ -806,9 +809,114 @@ class ProviderQuickSuggest extends UrlbarProvider {
query: searchString,
});
await this.#applyRanking(suggestions);
return suggestions;
}
/**
* Apply ranking to suggestions by updating their scores.
*
* @param {Array} suggestions
* The suggestions to be ranked.
*/
async #applyRanking(suggestions) {
switch (lazy.UrlbarPrefs.get("quickSuggestRankingMode")) {
case "random":
this.#updateScoreRandomly(suggestions);
break;
case "interest":
await this.#updateScorebyRelevance(suggestions);
break;
case "default":
default:
// Do nothing.
break;
}
}
/**
* Only exposed for testing.
*
* @param {Array} suggestions
* The suggestions to be ranked.
*/
async _test_applyRanking(suggestions) {
await this.#applyRanking(suggestions);
}
/**
* Update score by randomly selecting a winner and boosting its score with
* the highest score among the candidates plus a small addition.
*
* @param {Array} suggestions
* The suggestions to be ranked.
*/
#updateScoreRandomly(suggestions) {
if (suggestions.length <= 1) {
return;
}
const winner = suggestions[Math.floor(Math.random() * suggestions.length)];
const oldScore = winner.score;
const highest = Math.max(
...suggestions.map(suggestion => suggestion.score || 0)
);
winner.score = highest + 0.001;
this.logger.debug(
`Updated the suggestion score from '${oldScore}' to '${winner.score.toFixed(
3
)}'`
);
}
/**
* Update score by interest-based relevance scoring. The final score is a mean
* between the interest-based score and the default static score, which means
* if the former is 0 or less than the latter, the combined score will be less
* than the static score.
*
* @param {Array} suggestions
* The suggestions to be ranked.
*/
async #updateScorebyRelevance(suggestions) {
for (let suggestion of suggestions) {
if (suggestion.categories?.length) {
// UniFFI currently uses 1-based encoding for enums regardless of how
// it's defined upstream. Manually adjust that until that off-by-1
// handling gets fixed in the future.
//
// `INCONCLUSIVE` should be 0 as defined by upstream. If not, increment
// the categories by 1 provided by Merino or Remote Settings as they
// are guaranteed to use the correct encoding.
let categories = suggestion.categories;
if (lazy.Interest.INCONCLUSIVE !== 0) {
categories = categories.map(category => ++category);
}
try {
let score = await lazy.ContentRelevancyManager.score(categories);
let oldScore = suggestion.score;
if (isNaN(oldScore)) {
oldScore = DEFAULT_SUGGESTION_SCORE;
}
suggestion.score = (oldScore + score) / 2;
this.logger.debug(
`Updated the suggestion score from '${oldScore}' to '${suggestion.score.toFixed(
2
)}'`
);
} catch (error) {
this.logger.error(
`Failed to update the suggestion score: '${error}'`
);
continue;
}
}
}
}
/**
* Returns whether a given suggestion can be added for a query, assuming the
* provider itself should be active.

View file

@ -586,6 +586,49 @@ class _QuickSuggestTestUtils {
return result;
}
/**
* Returns an expected dynamic Wikipedia (non-sponsored) result that can be
* passed to `check_results()` in xpcshell tests.
*
* @returns {object}
* An object that can be passed to `check_results()`.
*/
dynamicWikipediaResult({
source = "merino",
provider = "wikipedia",
keyword = "wikipedia",
fullKeyword = keyword,
title = "Wikipedia Suggestion",
url = "https://example.com/wikipedia",
icon = null,
suggestedIndex = -1,
isSuggestedIndexRelativeToGroup = true,
} = {}) {
return {
suggestedIndex,
isSuggestedIndexRelativeToGroup,
type: lazy.UrlbarUtils.RESULT_TYPE.URL,
source: lazy.UrlbarUtils.RESULT_SOURCE.SEARCH,
heuristic: false,
payload: {
title,
url,
source,
provider,
icon,
displayUrl: url.replace(/^https:\/\//, ""),
isSponsored: false,
qsSuggestion: fullKeyword ?? keyword,
isBlockable: true,
blockL10n: {
id: "urlbar-result-menu-dismiss-firefox-suggest",
},
isManageable: true,
telemetryType: "wikipedia",
},
};
}
/**
* Returns an AMO (addons) suggestion suitable for storing in a remote
* settings attachment.

View file

@ -0,0 +1,211 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
// Tests relevance ranking integration with UrlbarProviderQuickSuggest.
"use strict";
const lazy = {};
ChromeUtils.defineESModuleGetters(lazy, {
ContentRelevancyManager:
"resource://gre/modules/ContentRelevancyManager.sys.mjs",
InterestVector: "resource://gre/modules/RustRelevancy.sys.mjs",
});
const PREF_CONTENT_RELEVANCY_ENABLED = "toolkit.contentRelevancy.enabled";
const PREF_RANKING_MODE = "browser.urlbar.quicksuggest.rankingMode";
function makeTestSuggestions() {
return [
{
title: "suggestion_about_education",
categories: [6], // "Education"
score: 0.2,
},
{
title: "suggestion_about_animals",
categories: [1], // "Animals"
score: 0.2,
},
];
}
const MERINO_SUGGESTIONS = [
{
provider: "adm",
full_keyword: "amp",
title: "Amp Suggestion",
url: "https://example.com/amp",
icon: null,
impression_url: "https://example.com/amp-impression",
click_url: "https://example.com/amp-click",
block_id: 1,
advertiser: "Amp",
iab_category: "22 - Shopping",
is_sponsored: true,
categories: [1], // Animals
score: 0.3,
},
{
title: "Wikipedia Suggestion",
url: "https://example.com/wikipedia",
provider: "wikipedia",
full_keyword: "wikipedia",
icon: null,
block_id: 0,
advertiser: "dynamic-Wikipedia",
is_sponsored: false,
categories: [6], // Education
score: 0.23,
},
];
const SEARCH_STRING = "frab";
const EXPECTED_AMP_RESULT = QuickSuggestTestUtils.ampResult({
source: "merino",
provider: "adm",
requestId: "request_id",
});
const EXPECTED_WIKIPEDIA_RESULT =
QuickSuggestTestUtils.dynamicWikipediaResult();
let gSandbox;
add_setup(async () => {
await QuickSuggestTestUtils.ensureQuickSuggestInit({
merinoSuggestions: MERINO_SUGGESTIONS,
prefs: [
["suggest.quicksuggest.nonsponsored", true],
["suggest.quicksuggest.sponsored", true],
],
});
gSandbox = sinon.createSandbox();
const fakeStore = {
close: gSandbox.fake(),
userInterestVector: gSandbox.stub(),
};
const rustRelevancyStore = {
init: gSandbox.fake.returns(fakeStore),
};
fakeStore.userInterestVector.resolves(
new lazy.InterestVector({
animals: 0,
arts: 0,
autos: 0,
business: 0,
career: 0,
education: 50,
fashion: 0,
finance: 0,
food: 0,
government: 0,
hobbies: 0,
home: 0,
news: 0,
realEstate: 0,
society: 0,
sports: 0,
tech: 0,
travel: 0,
inconclusive: 0,
})
);
Services.prefs.setBoolPref(PREF_CONTENT_RELEVANCY_ENABLED, true);
lazy.ContentRelevancyManager.init(rustRelevancyStore);
registerCleanupFunction(() => {
lazy.ContentRelevancyManager.uninit();
Services.prefs.clearUserPref(PREF_CONTENT_RELEVANCY_ENABLED);
gSandbox.restore();
});
});
add_task(async function test_interest_mode() {
Services.prefs.setStringPref(PREF_RANKING_MODE, "interest");
const suggestions = makeTestSuggestions();
await UrlbarProviderQuickSuggest._test_applyRanking(suggestions);
Assert.greater(
suggestions[0].score,
0.2,
"The score should be boosted for relevant suggestions"
);
Assert.less(
suggestions[1].score,
0.2,
"The score should not be lowered for irrelevant suggestion"
);
Services.prefs.clearUserPref(PREF_RANKING_MODE);
});
add_task(async function test_default_mode() {
Services.prefs.setStringPref(PREF_RANKING_MODE, "default");
const suggestions = makeTestSuggestions();
await UrlbarProviderQuickSuggest._test_applyRanking(suggestions);
Assert.equal(
suggestions[0].score,
0.2,
"The score should be unchanged for the default mode"
);
Assert.equal(
suggestions[1].score,
0.2,
"The score should be unchanged for the default mode"
);
Services.prefs.clearUserPref(PREF_RANKING_MODE);
});
add_task(async function test_random_mode() {
Services.prefs.setStringPref(PREF_RANKING_MODE, "random");
const suggestions = makeTestSuggestions();
await UrlbarProviderQuickSuggest._test_applyRanking(suggestions);
const highest = Math.max(...suggestions.map(suggestion => suggestion.score));
Assert.greater(highest, 0.2, "The highest score should be boosted");
Services.prefs.clearUserPref(PREF_RANKING_MODE);
});
add_task(async function test_default_mode_end2end() {
Services.prefs.setStringPref(PREF_RANKING_MODE, "default");
let context = createContext(SEARCH_STRING, {
providers: [UrlbarProviderQuickSuggest.name],
isPrivate: false,
});
await check_results({
context,
matches: [EXPECTED_AMP_RESULT],
});
Services.prefs.clearUserPref(PREF_RANKING_MODE);
});
add_task(async function test_interest_mode_end2end() {
Services.prefs.setStringPref(PREF_RANKING_MODE, "interest");
let context = createContext(SEARCH_STRING, {
providers: [UrlbarProviderQuickSuggest.name],
isPrivate: false,
});
await check_results({
context,
matches: [EXPECTED_WIKIPEDIA_RESULT],
});
Services.prefs.clearUserPref(PREF_RANKING_MODE);
});

View file

@ -42,6 +42,8 @@ skip-if = ["true"] # Bug 1880214
["test_quicksuggest_positionInSuggestions.js"]
skip-if = ["true"] # Bug 1880214
["test_quicksuggest_relevanceRanking.js"]
["test_quicksuggest_scoreMap.js"]
["test_quicksuggest_topPicks.js"]

View file

@ -45,6 +45,8 @@ support-files = [
["browser_address_doorhanger_unsupported_region.js"]
["browser_address_heuristics_autofill_name.js"]
["browser_address_telemetry.js"]
["browser_autofill_whenhidden.js"]

View file

@ -0,0 +1,263 @@
/* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
requestLongerTimeout(2);
add_setup(async function () {
await SpecialPowers.pushPrefEnv({
set: [
["extensions.formautofill.addresses.enabled", true],
["extensions.formautofill.addresses.supported", "on"],
],
});
});
add_heuristic_tests([
{
description: `(FR) name should be updated to family-name in context of given-name`,
fixtureData: `
<form>
<input id="lastName">
<label for="lastName" >Nom</label>
<input id="firstName">
<label for="firstName" >Prénom</label>
<label for="middleName" >"Middle"</label>
<input id=middleName>
<label for="phoneNumber" >"N° de téléphone"</label>
<input id=phoneNumber>
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "family-name",
reason: "update-heuristic",
},
{
fieldName: "given-name",
reason: "regex-heuristic",
},
{
fieldName: "additional-name",
reason: "regex-heuristic",
},
{
fieldName: "tel",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `(FR) name should be updated to family-name in context of given-name`,
fixtureData: `
<form>
<input id="lastName">
<label for="lastName" >Nom</label>
<input id="firstName">
<label for="firstName" >Prénom</label>
<input id=middleName>
<label for="middleName" >"Middle"</label>
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "family-name",
reason: "update-heuristic",
},
{
fieldName: "given-name",
reason: "regex-heuristic",
},
{
fieldName: "additional-name",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `(DE) name should be updated to family-name in context of given-name`,
fixtureData: `
<form>
<input placeholder="Name">
<input placeholder="Vorname">
<input placeholder="Address">
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "family-name",
reason: "update-heuristic",
},
{
fieldName: "given-name",
reason: "regex-heuristic",
},
{
fieldName: "street-address",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `(DE) name should not be updated to family-name if given-name not present`,
fixtureData: `
<form>
<input placeholder="Name">
<input placeholder="Address">
<input placeholder="City">
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "name",
reason: "regex-heuristic",
},
{
fieldName: "street-address",
reason: "regex-heuristic",
},
{
fieldName: "address-level2",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `(DE) name should be corrected to family-name in context of given-name`,
fixtureData: `
<form>
<input placeholder="Vorname">
<input placeholder="Name">
<input placeholder="email">
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "given-name",
reason: "regex-heuristic",
},
{
fieldName: "family-name",
reason: "update-heuristic",
},
{
fieldName: "email",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `name should be corrected to family-name in context of given-name (1)`,
fixtureData: `
<form>
<input placeholder="First Name">
<input placeholder="Name">
<input placeholder="email">
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "given-name",
reason: "regex-heuristic",
},
{
fieldName: "family-name",
reason: "update-heuristic",
},
{
fieldName: "email",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `name should be corrected to family-name in context of given-name (2)`,
fixtureData: `
<form>
<input placeholder="Name">
<input placeholder="First Name">
<input placeholder="email">
</form>`,
expectedResult: [
{
fields: [
{
fieldName: "family-name",
reason: "update-heuristic",
},
{
fieldName: "given-name",
reason: "regex-heuristic",
},
{
fieldName: "email",
reason: "regex-heuristic",
},
],
},
],
},
{
description: `two adjacent name sections: name(0) is invalid and not filled, name(1) is a new section and detected as name`,
fixtureData: `
<form>
<input placeholder="Name">
<input placeholder="Name">
<input placeholder="Email">
<input placeholder="Phone">
</form>`,
expectedResult: [
{
invalid: true,
fields: [
{
fieldName: "name",
reason: "regex-heuristic",
},
],
},
{
fields: [
{
fieldName: "name",
reason: "regex-heuristic",
},
{
fieldName: "email",
reason: "regex-heuristic",
},
{
fieldName: "tel",
reason: "regex-heuristic",
},
],
},
],
},
]);

View file

@ -587,6 +587,7 @@ const AVAILABLE_INJECTIONS = [
"*://*.lafoodbank.org/*", // 127006
"*://rutamayacoffee.com/*", // 129353
"*://ottoandspike.com.au/*", // bugzilla 1644602
"*://give.umrelief.org/give/*", // bugzilla 1916407
],
js: [
{
@ -1046,6 +1047,20 @@ const AVAILABLE_INJECTIONS = [
],
},
},
{
id: "1922175",
platform: "all",
domain: "app.livingsecurity.com",
bug: "1922175",
contentScripts: {
matches: ["*://app.livingsecurity.com/*"],
js: [
{
file: "injections/js/bug1896383-error-capturestacktrace-shim.js",
},
],
},
},
{
id: "bug1889326",
platform: "desktop",
@ -1175,6 +1190,34 @@ const AVAILABLE_INJECTIONS = [
],
},
},
{
id: "bug1886616",
platform: "all",
domain: "www.six-group.com",
bug: "1886616",
contentScripts: {
matches: ["*://www.six-group.com/*/market-data/etf/etf-explorer.html*"],
css: [
{
file: "injections/css/bug1886616-www.six-group.com-select-fix.css",
},
],
},
},
{
id: "bug1896349",
platform: "all",
domain: "vivaldi.com",
bug: "1896349",
contentScripts: {
matches: ["*://vivaldi.com/*"],
css: [
{
file: "injections/css/bug1896349-vivaldi.com-selected-text-fix.css",
},
],
},
},
];
module.exports = AVAILABLE_INJECTIONS;

View file

@ -1404,6 +1404,42 @@ const AVAILABLE_UA_OVERRIDES = [
},
},
},
{
/*
* Bug 1919004 - UA override for www.editoracontexto.com.br
* Webcompat issue #141641 - https://webcompat.com/issues/141641
*
* Site presents its desktop CSS to Firefox on Android.
*/
id: "bug1919004",
platform: "android",
domain: "www.editoracontexto.com.br",
bug: "1919004",
config: {
matches: ["*://www.editoracontexto.com.br/*"],
uaTransformer: () => {
return UAHelpers.getDeviceAppropriateChromeUA();
},
},
},
{
/*
* Bug 1921410 - UA override for beta.maps.apple.com
* Webcompat issue #140205 - https://webcompat.com/issues/140205
*
* Apple Maps beta artifically blocks Linux.
*/
id: "bug1921410",
platform: "linux",
domain: "beta.maps.apple.com",
bug: "1921410",
config: {
matches: ["*://beta.maps.apple.com/*"],
uaTransformer: originalUA => {
return UAHelpers.getWindowsUA(originalUA);
},
},
},
];
module.exports = AVAILABLE_UA_OVERRIDES;

View file

@ -0,0 +1,15 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
/**
* www.six-group.com - Selected input values are hidden
* Bug #1886616 - https://bugzilla.mozilla.org/show_bug.cgi?id=1886616
* WebCompat issue #129271 - https://webcompat.com/issues/129271
*
* The page is hiding CSS content, which is not interoperable. In this
* case, it causes their select dropdown's values to be hidden.
*/
select {
content: normal;
}

View file

@ -0,0 +1,13 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
/**
* vivaldi.com - Selected text is invisible
* Bug #1896349 - https://bugzilla.mozilla.org/show_bug.cgi?id=1896349
* WebCompat issue #136863 - https://webcompat.com/issues/136863
*/
::selection {
color: HighlightText;
background-color: Highlight;
}

View file

@ -144,13 +144,14 @@ class UAOverrides {
async registerUAOverrides() {
const platformMatches = ["all"];
let platformInfo = await browser.runtime.getPlatformInfo();
platformMatches.push(platformInfo.os == "android" ? "android" : "desktop");
const { os } = await browser.runtime.getPlatformInfo();
platformMatches.push(os);
platformMatches.push(os == "android" ? "android" : "desktop");
for (const override of this._availableOverrides) {
if (platformMatches.includes(override.platform)) {
override.availableOnPlatform = true;
override.currentPlatform = platformInfo.os;
override.currentPlatform = os;
// If there is a specific about:config preference governing
// this override, monitor its state.

View file

@ -2,7 +2,7 @@
"manifest_version": 2,
"name": "Web Compatibility Interventions",
"description": "Urgent post-release fixes for web compatibility.",
"version": "130.5.0",
"version": "133.0.0",
"browser_specific_settings": {
"gecko": {
"id": "webcompat@mozilla.org",

View file

@ -73,7 +73,9 @@ FINAL_TARGET_FILES.features["webcompat@mozilla.org"]["injections"]["css"] += [
"injections/css/bug1849388-kucharkaprodceru.cz-scroll-fix.css",
"injections/css/bug1868345-tvmovie.de-scroll-fix.css",
"injections/css/bug1884842-foodora.cz-height-fix.css",
"injections/css/bug1886616-www.six-group.com-select-fix.css",
"injections/css/bug1895994-softtrans.ro-unlock-scrolling.css",
"injections/css/bug1896349-vivaldi.com-selected-text-fix.css",
"injections/css/bug1896571-gracobaby.ca-unlock-scrolling.css",
]

View file

@ -16,7 +16,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"af": {
"pin": false,
@ -35,7 +35,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"an": {
"pin": false,
@ -54,7 +54,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ar": {
"pin": false,
@ -73,7 +73,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ast": {
"pin": false,
@ -92,7 +92,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"az": {
"pin": false,
@ -111,7 +111,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"be": {
"pin": false,
@ -130,7 +130,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"bg": {
"pin": false,
@ -149,7 +149,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"bn": {
"pin": false,
@ -168,7 +168,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"bo": {
"pin": false,
@ -187,7 +187,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"br": {
"pin": false,
@ -206,7 +206,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"brx": {
"pin": false,
@ -225,7 +225,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"bs": {
"pin": false,
@ -244,7 +244,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ca": {
"pin": false,
@ -263,7 +263,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ca-valencia": {
"pin": false,
@ -282,7 +282,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"cak": {
"pin": false,
@ -301,7 +301,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ckb": {
"pin": false,
@ -320,7 +320,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"cs": {
"pin": false,
@ -339,7 +339,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"cy": {
"pin": false,
@ -358,7 +358,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"da": {
"pin": false,
@ -377,7 +377,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"de": {
"pin": false,
@ -396,7 +396,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"dsb": {
"pin": false,
@ -415,7 +415,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"el": {
"pin": false,
@ -434,7 +434,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"en-CA": {
"pin": false,
@ -453,7 +453,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"en-GB": {
"pin": false,
@ -472,7 +472,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"eo": {
"pin": false,
@ -491,7 +491,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"es-AR": {
"pin": false,
@ -510,7 +510,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"es-CL": {
"pin": false,
@ -529,7 +529,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"es-ES": {
"pin": false,
@ -548,7 +548,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"es-MX": {
"pin": false,
@ -567,7 +567,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"et": {
"pin": false,
@ -586,7 +586,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"eu": {
"pin": false,
@ -605,7 +605,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"fa": {
"pin": false,
@ -624,7 +624,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ff": {
"pin": false,
@ -643,7 +643,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"fi": {
"pin": false,
@ -662,7 +662,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"fr": {
"pin": false,
@ -681,7 +681,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"fur": {
"pin": false,
@ -700,7 +700,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"fy-NL": {
"pin": false,
@ -719,7 +719,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ga-IE": {
"pin": false,
@ -738,7 +738,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"gd": {
"pin": false,
@ -757,7 +757,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"gl": {
"pin": false,
@ -776,7 +776,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"gn": {
"pin": false,
@ -795,7 +795,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"gu-IN": {
"pin": false,
@ -814,7 +814,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"he": {
"pin": false,
@ -833,7 +833,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"hi-IN": {
"pin": false,
@ -852,7 +852,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"hr": {
"pin": false,
@ -871,7 +871,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"hsb": {
"pin": false,
@ -890,7 +890,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"hu": {
"pin": false,
@ -909,7 +909,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"hy-AM": {
"pin": false,
@ -928,7 +928,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"hye": {
"pin": false,
@ -947,7 +947,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ia": {
"pin": false,
@ -966,7 +966,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"id": {
"pin": false,
@ -985,7 +985,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"is": {
"pin": false,
@ -1004,7 +1004,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"it": {
"pin": false,
@ -1023,7 +1023,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ja": {
"pin": false,
@ -1040,7 +1040,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ja-JP-mac": {
"pin": false,
@ -1048,7 +1048,7 @@
"macosx64",
"macosx64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ka": {
"pin": false,
@ -1067,7 +1067,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"kab": {
"pin": false,
@ -1086,7 +1086,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"kk": {
"pin": false,
@ -1105,7 +1105,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"km": {
"pin": false,
@ -1124,7 +1124,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"kn": {
"pin": false,
@ -1143,7 +1143,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ko": {
"pin": false,
@ -1162,7 +1162,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"lij": {
"pin": false,
@ -1181,7 +1181,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"lo": {
"pin": false,
@ -1200,7 +1200,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"lt": {
"pin": false,
@ -1219,7 +1219,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ltg": {
"pin": false,
@ -1238,7 +1238,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"lv": {
"pin": false,
@ -1257,7 +1257,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"meh": {
"pin": false,
@ -1276,7 +1276,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"mk": {
"pin": false,
@ -1295,7 +1295,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"mr": {
"pin": false,
@ -1314,7 +1314,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ms": {
"pin": false,
@ -1333,7 +1333,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"my": {
"pin": false,
@ -1352,7 +1352,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"nb-NO": {
"pin": false,
@ -1371,7 +1371,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ne-NP": {
"pin": false,
@ -1390,7 +1390,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"nl": {
"pin": false,
@ -1409,7 +1409,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"nn-NO": {
"pin": false,
@ -1428,7 +1428,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"oc": {
"pin": false,
@ -1447,7 +1447,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"pa-IN": {
"pin": false,
@ -1466,7 +1466,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"pl": {
"pin": false,
@ -1485,7 +1485,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"pt-BR": {
"pin": false,
@ -1504,7 +1504,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"pt-PT": {
"pin": false,
@ -1523,7 +1523,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"rm": {
"pin": false,
@ -1542,7 +1542,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ro": {
"pin": false,
@ -1561,7 +1561,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ru": {
"pin": false,
@ -1580,7 +1580,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sat": {
"pin": false,
@ -1599,7 +1599,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sc": {
"pin": false,
@ -1618,7 +1618,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"scn": {
"pin": false,
@ -1637,7 +1637,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sco": {
"pin": false,
@ -1656,7 +1656,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"si": {
"pin": false,
@ -1675,7 +1675,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sk": {
"pin": false,
@ -1694,7 +1694,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"skr": {
"pin": false,
@ -1713,7 +1713,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sl": {
"pin": false,
@ -1732,7 +1732,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"son": {
"pin": false,
@ -1751,7 +1751,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sq": {
"pin": false,
@ -1770,7 +1770,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sr": {
"pin": false,
@ -1789,7 +1789,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"sv-SE": {
"pin": false,
@ -1808,7 +1808,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"szl": {
"pin": false,
@ -1827,7 +1827,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ta": {
"pin": false,
@ -1846,7 +1846,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"te": {
"pin": false,
@ -1865,7 +1865,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"tg": {
"pin": false,
@ -1884,7 +1884,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"th": {
"pin": false,
@ -1903,7 +1903,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"tl": {
"pin": false,
@ -1922,7 +1922,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"tr": {
"pin": false,
@ -1941,7 +1941,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"trs": {
"pin": false,
@ -1960,7 +1960,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"uk": {
"pin": false,
@ -1979,7 +1979,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"ur": {
"pin": false,
@ -1998,7 +1998,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"uz": {
"pin": false,
@ -2017,7 +2017,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"vi": {
"pin": false,
@ -2036,7 +2036,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"wo": {
"pin": false,
@ -2055,7 +2055,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"xh": {
"pin": false,
@ -2074,7 +2074,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"zh-CN": {
"pin": false,
@ -2093,7 +2093,7 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
},
"zh-TW": {
"pin": false,
@ -2112,6 +2112,6 @@
"win64-aarch64-devedition",
"win64-devedition"
],
"revision": "a7ea382524763a85f4fabc83b1245fcceb537497"
"revision": "4c0f1081640fe9a8a7f7689d1d964c12b14d4195"
}
}

View file

@ -173,7 +173,7 @@ body {
/* Reset linux padding */
padding: 0;
&:not(.titlebar-color) {
&:not(.browser-titlebar) {
background-color: var(--toolbar-bgcolor);
color: var(--toolbar-color);
border-style: none;
@ -303,7 +303,6 @@ body {
/* The toolbar buttons that animate use position:absolute and require a
* positioned #nav-bar. */
position: relative;
z-index: var(--browser-area-z-index-toolbox);
border-top: 0.01px var(--tabs-navbar-separator-style) var(--tabs-navbar-separator-color);
&[tabs-hidden] {

View file

@ -233,6 +233,7 @@
skin/classic/browser/tabbrowser/tab-connecting.png (../shared/tabbrowser/tab-connecting.png)
skin/classic/browser/tabbrowser/tab-connecting@2x.png (../shared/tabbrowser/tab-connecting@2x.png)
skin/classic/browser/tabbrowser/tab-drag-indicator.svg (../shared/tabbrowser/tab-drag-indicator.svg)
skin/classic/browser/tabbrowser/tab-group-chicklet.svg (../shared/tabbrowser/tab-group-chicklet.svg)
skin/classic/browser/tabbrowser/tab-hover-preview.css (../shared/tabbrowser/tab-hover-preview.css)
skin/classic/browser/tabbrowser/tab-loading.png (../shared/tabbrowser/tab-loading.png)
skin/classic/browser/tabbrowser/tab-loading@2x.png (../shared/tabbrowser/tab-loading@2x.png)

View file

@ -0,0 +1,7 @@
<!-- This Source Code Form is subject to the terms of the Mozilla Public
- License, v. 2.0. If a copy of the MPL was not distributed with this
- file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
<svg xmlns="http://www.w3.org/2000/svg"
width="16" height="16" viewBox="0 0 16 16">
<rect width="16" height="16" rx="4" fill="context-fill"/>
</svg>

After

Width:  |  Height:  |  Size: 368 B

View file

@ -21,6 +21,7 @@
--tab-pinned-container-margin-inline-expanded: var(--space-small);
--tab-border-radius: 4px;
--tab-overflow-clip-margin: 2px;
--tab-close-button-padding: 6px;
--tab-shadow-max-size: 6px;
--tab-block-margin: 4px;
--tab-icon-end-margin: 5.5px;
@ -555,7 +556,7 @@
margin-inline-end: calc(var(--tab-inline-padding) / -2);
width: 24px;
height: 24px;
padding: 6px;
padding: var(--tab-close-button-padding);
border-radius: var(--tab-border-radius);
list-style-image: url(chrome://global/skin/icons/close-12.svg);
@ -1097,6 +1098,10 @@ tab-group {
height: var(--tab-min-height);
}
.tab-close-button {
margin-inline-end: calc(-1 * var(--tab-close-button-padding));
}
&:not([expanded]) {
.tabbrowser-tab {
padding: 0;
@ -1375,3 +1380,9 @@ toolbar:not(#TabsToolbar) #firefox-view-button {
}
}
}
.tab-contextmenu-group-icon {
list-style-image: url("chrome://browser/skin/tabbrowser/tab-group-chicklet.svg");
-moz-context-properties: fill;
fill: light-dark(var(--tab-group-color), var(--tab-group-color-invert));
}

View file

@ -3,4 +3,4 @@ subsuite = "screenshots"
support-files = ["../head.js"]
["browser_devtools.js"]
skip-if = ["os == 'mac'"] # times out on macosx1014, see 1570100
skip-if = ["os == 'mac' && os_version == '10.15' && processor == 'x86_64'"] # times out on macosx1014, see 1570100

View file

@ -76,9 +76,9 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-breakpoints-popup.js"]
skip-if = [
"os == 'linux' && debug", # Bug 1750199
"tsan", # Bug 1750199
"apple_catalina && !debug", # Bug 1767705
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && debug", # Bug 1750199
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && tsan", # Bug 1750199
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt", # Bug 1767705
]
["browser_dbg-breakpoints-reloading-with-source-changes.js"]
@ -98,7 +98,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-browser-toolbox-unselected-pause.js"]
skip-if = [
"asan", # Bug 1591064
"os == 'win' && fission && debug", # intermittent on fission, Bug 1720165 - test timed out
"os == 'win' && debug", # intermittent on fission, Bug 1720165 - test timed out
]
["browser_dbg-browser-toolbox-workers.js"]
@ -187,7 +187,6 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-expressions-thread.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
skip-if = ["!fission"] # threads panel only shows remote frame when fission is enabled.
["browser_dbg-expressions-watch.js"]
@ -200,8 +199,8 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-features-breakable-lines.js"]
skip-if = [
"os == 'linux' && os_version == '18.04' && !debug", # Bug 1767701
"apple_catalina && !debug", # Bug 1767701
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt", # Bug 1767701
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt", # Bug 1767701
]
["browser_dbg-features-breakable-positions.js"]

View file

@ -32,7 +32,7 @@ prefs = [
["browser_dbg-link-reload.js"]
skip-if = [
"os == 'linux' && asan", # Bug 1715866
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && asan", # Bug 1715866
"os == 'win' && bits == 64", # Bug 1715866
]
@ -59,17 +59,17 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-navigation.js"]
skip-if = [
"verify && debug && os == 'mac'", # Bug 1307249
"os == 'linux' && debug && bits == 64", # Bug 1307249
"os == 'mac' && debug", # Bug 1307249
"os == 'mac' && debug && verify", # Bug 1307249
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1307249
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && debug", # Bug 1307249
]
["browser_dbg-no-duplicate-breakpoints-on-frame-reload.js"]
["browser_dbg-old-breakpoint.js"]
skip-if = [
"os == 'linux'", #Bug 1644044
"os == 'mac'", #Bug 1644044
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", #Bug 1644044
"os == 'mac' && os_version == '10.15' && processor == 'x86_64'", #Bug 1644044
]
["browser_dbg-outline-filter.js"]
@ -144,8 +144,8 @@ fail-if = ["a11y_checks"] # Bug 1860733 splitter element is not focusable
["browser_dbg-preview.js"]
skip-if = [
"os == 'win'",
"os == 'linux'",
"os == 'mac' && !debug",
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'",
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt",
]
["browser_dbg-project-root.js"]
@ -156,19 +156,22 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-quick-open.js"]
skip-if = [
"os == 'win'",
"os == 'linux' && bits == 64 && debug", # Bug 1721999
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && debug", # Bug 1721999
]
["browser_dbg-react-app.js"]
skip-if = [
"os == 'win'",
"os == 'linux' && tsan", # Bug 1813196
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && tsan", # Bug 1813196
]
["browser_dbg-react-jsx.js"]
["browser_dbg-reducer-cleanup-on-target-removal.js"]
skip-if = ["os == 'linux' && (debug || tsan)"] # Bug 1835255
skip-if = [
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && debug", # Bug 1835255
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && tsan", # Bug 1835255
]
["browser_dbg-reloading.js"]
skip-if = ["true"]
@ -224,7 +227,7 @@ skip-if = [
"ccov",
"debug",
"tsan",
"verify && debug && os == 'linux'",
"os == 'linux' && debug && verify",
"a11y_checks", # Bugs 1858041 and 1849028 intermittent results (fails on Try, passes on Autoland)
]
@ -234,7 +237,7 @@ skip-if = ["true"] # original stepping is currently disabled
["browser_dbg-sourcemapped-toggle.js"]
["browser_dbg-sourcemaps-bogus.js"]
skip-if = ["os == 'linux' && !asan"] # bug 1447118
skip-if = ["os == 'linux' && os_version == '18.04' && processor == 'x86_64' && !asan"] # bug 1447118
["browser_dbg-sourcemaps-breakpoints.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
@ -277,7 +280,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_dbg-stepping.js"]
skip-if = [
"debug",
"verify && os == 'win'",
"os == 'win' && verify",
]
["browser_dbg-tabs-keyboard.js"]
@ -303,14 +306,14 @@ skip-if = ["true"] # Bug 1814093
["browser_dbg-windowless-service-workers-reload.js"]
skip-if = [
"os == 'linux'", # Bug 1767716
"win11_2009 && !debug", # Bug 1767716
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1767716
"win11_2009 && opt", # Bug 1767716
]
["browser_dbg-windowless-service-workers.js"]
skip-if = [
"os == 'linux'", # Bug 1732486, # Bug 1767717
"win11_2009 && !debug", # Bug 1767717
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1732486, # Bug 1767717
"win11_2009 && opt", # Bug 1767717
]
["browser_dbg-windowless-workers-early-breakpoint.js"]

View file

@ -35,8 +35,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_computed_getNodeInfo.js"]
skip-if = [
"apple_catalina && !debug", #Bug 1559033
"apple_silicon && !debug", #Bug 1559033
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt", #Bug 1559033
"a11y_checks", # Bugs 1849028 and 1858041 to investigate intermittent a11y_checks results
]

View file

@ -32,7 +32,10 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_grids_grid-list-no-grids.js"]
["browser_grids_grid-list-on-iframe-reloaded.js"]
skip-if = ["verify && (os == 'win' || os == 'linux')"]
skip-if = [
"os == 'win' && verify",
"os == 'linux' && verify",
]
["browser_grids_grid-list-on-mutation-element-added.js"]
skip-if = ["true"] #Bug 1557326
@ -65,13 +68,14 @@ skip-if = ["true"] #Bug 1557326
["browser_grids_grid-outline-updates-on-grid-change.js"]
skip-if = [
"os == 'linux'",
"os == 'mac'",
"os == 'win' && (debug || asan)", #Bug 1557181
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'",
"os == 'mac' && os_version == '10.15' && processor == 'x86_64'",
"os == 'win' && debug", #Bug 1557181
"os == 'win' && asan", #Bug 1557181
]
["browser_grids_grid-outline-writing-mode.js"]
skip-if = ["verify && os == 'win'"]
skip-if = ["os == 'win' && verify"]
["browser_grids_highlighter-setting-rules-grid-toggle.js"]

View file

@ -86,13 +86,13 @@ support-files = [
]
["browser_markup_accessibility_focus_blur.js"]
skip-if = ["os == 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
run-if = ["os != 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
["browser_markup_accessibility_navigation.js"]
skip-if = ["os == 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
run-if = ["os != 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
["browser_markup_accessibility_navigation_after_edit.js"]
skip-if = ["os == 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
run-if = ["os != 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
["browser_markup_accessibility_new_selection.js"]

View file

@ -38,7 +38,7 @@ skip-if = [
["browser_rules_add-property-cancel_03.js"]
["browser_rules_add-property-commented.js"]
skip-if = ["verify && debug && os == 'win'"]
skip-if = ["os == 'win' && debug && verify"]
["browser_rules_add-property-invalid-identifier.js"]
@ -78,8 +78,8 @@ skip-if = ["verify && debug && os == 'win'"]
["browser_rules_authored_color.js"]
skip-if = [
"os == 'linux' && os_version == '18.04' && !debug", # Bug 1559315
"apple_catalina", # Bug 1713158
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt", # Bug 1559315
"os == 'mac' && os_version == '10.15' && processor == 'x86_64'", # Bug 1713158
"win11_2009", # Bug 1797751
]
@ -106,7 +106,7 @@ skip-if = [
["browser_rules_colorUnit.js"]
["browser_rules_color_scheme_simulation.js"]
skip-if = ["os == 'win' && !debug"] # Bug 1703465
skip-if = ["os == 'win' && opt"] # Bug 1703465
["browser_rules_color_scheme_simulation_bfcache.js"]
@ -153,7 +153,7 @@ skip-if = ["os == 'win' && !debug"] # Bug 1703465
["browser_rules_completion-new-property_01.js"]
["browser_rules_completion-new-property_02.js"]
skip-if = ["verify && !debug && os == 'win'"]
skip-if = ["os == 'win' && opt && verify"]
["browser_rules_completion-new-property_03.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
@ -221,7 +221,7 @@ skip-if = ["a11y_checks"] # Bugs 1849028 and 1858041 clicked span.ruleview-expan
["browser_rules_edit-property-order.js"]
["browser_rules_edit-property-remove_01.js"]
skip-if = ["verify && debug && os == 'win'"]
skip-if = ["os == 'win' && debug && verify"]
["browser_rules_edit-property-remove_02.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
@ -252,7 +252,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_rules_edit-property_10.js"]
["browser_rules_edit-selector-click-on-scrollbar.js"]
skip-if = ["os == 'mac'"] # Bug 1245996 : click on scrollbar not working on OSX
skip-if = ["os == 'mac' && os_version == '10.15' && processor == 'x86_64'"] # Bug 1245996 : click on scrollbar not working on OSX
["browser_rules_edit-selector-click.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
@ -322,6 +322,5 @@ skip-if = ["debug"] # Bug 1250058 - Docshell leak on debug
["browser_rules_variables_04-valid-chars.js"]
["browser_rules_variables_autocomplete.js"]
skip-if = ["!fission"]
["browser_rules_variables_host.js"]

View file

@ -73,7 +73,7 @@ support-files = [
["browser_inspector_breadcrumbs_keybinding.js"]
["browser_inspector_breadcrumbs_keyboard_trap.js"]
skip-if = ["os == 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
run-if = ["os != 'mac'"] # Full keyboard navigation on OSX only works if Full Keyboard Access setting is set to All Control in System Keyboard Preferences
["browser_inspector_breadcrumbs_mutations.js"]
@ -149,8 +149,8 @@ skip-if = ["os == 'mac'"] # Full keyboard navigation on OSX only works if Full K
skip-if = [
"os == 'win' && asan", # Bug 1453214
"os == 'win' && debug", # Bug 1453214
"os == 'linux'", # Bug 1453214
"os == 'mac' && debug", # high frequency intermittent, bug 1453214
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1453214
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && debug", # high frequency intermittent, bug 1453214
]
["browser_inspector_highlighter-cssshape_05.js"]
@ -260,7 +260,7 @@ skip-if = ["os == 'win'"] # bug 1413442
["browser_inspector_highlighter-rulers_02.js"]
["browser_inspector_highlighter-rulers_03.js"]
skip-if = ["os == 'win' && !debug"] # Bug 1449754
skip-if = ["os == 'win' && opt"] # Bug 1449754
["browser_inspector_highlighter-selector_01.js"]
@ -433,7 +433,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_inspector_startup.js"]
["browser_inspector_switch-to-inspector-on-pick.js"]
skip-if = ["apple_catalina && !debug"] # Bug 1713158
skip-if = ["os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt"] # Bug 1713158
["browser_inspector_textbox-menu.js"]

View file

@ -21,9 +21,8 @@ support-files = [
["browser_net_har_copy_all_as_har.js"]
skip-if = [
"apple_catalina && !debug", #Bug 1622925
"apple_silicon && !debug", #Bug 1622925
"os == 'linux' && os_version == '18.04' && !debug", #Bug 1622925
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt", #Bug 1622925
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt", #Bug 1622925
"win11_2009", # Bug 1797751
]

View file

@ -133,11 +133,10 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_net_block-pattern.js"]
skip-if = [
"os == 'linux' && os_version == '18.04'",
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'",
"win11_2009 && debug", # Bug 1603355
"win10_2009 && debug", # Bug 1603355
"apple_catalina && debug", # Bug 1603355
"apple_silicon && debug", # Bug 1603355
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && debug", # Bug 1603355
]
["browser_net_block-serviceworker.js"]
@ -205,8 +204,7 @@ skip-if = [
["browser_net_content-type.js"]
skip-if = [
"apple_catalina && !debug",
"apple_silicon && !debug",
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt",
]
["browser_net_cookies_sorted.js"]
@ -225,8 +223,7 @@ skip-if = ["win11_2009 && debug && verify"]
["browser_net_copy_params.js"]
skip-if = [
"win11_2009", # Bug 1797751
"apple_catalina && !debug && verify", # bug 1328915
"apple_silicon && !debug && verify", # bug 1328915
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && opt && verify", # bug 1328915
]
["browser_net_copy_response.js"]
@ -425,7 +422,7 @@ skip-if = [
["browser_net_resend_xhr.js"]
["browser_net_response_CORS_blocked.js"]
skip-if = ["os == 'linux' && os_version == '18.04' && !debug && a11y_checks"] # bug 1732635
skip-if = ["os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt && a11y_checks"] # bug 1732635
["browser_net_response_node-expanded.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
@ -435,7 +432,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_net_script_cache.js"]
["browser_net_search-results.js"]
skip-if = ["os == 'linux' && os_version == '18.04' && a11y_checks"] # Bug 1721160
skip-if = ["os == 'linux' && os_version == '18.04' && processor == 'x86_64' && a11y_checks"] # Bug 1721160
["browser_net_security-details.js"]
@ -462,7 +459,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
["browser_net_service-worker-status.js"]
skip-if = ["os == 'linux' && os_version == '18.04' && !debug && verify"]
skip-if = ["os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt && verify"]
["browser_net_service-worker-timings.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled

View file

@ -98,8 +98,8 @@ skip-if = ["verify"]
["browser_console_webconsole_private_browsing.js"]
skip-if = [
"os == 'mac'", # Bug 1689000
"os == 'linux' && debug", # Bug 1689000
"os == 'mac' && os_version == '10.15' && processor == 'x86_64'", # Bug 1689000
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && debug", # Bug 1689000
]
["browser_console_webextension.js"]
@ -111,5 +111,5 @@ skip-if = [
"asan", # Bug 1591590
"debug", # Bug 1591590
"ccov", # Bug 1591590
"os == 'win' && bits == 64 && !debug", # Bug 1591590
"os == 'win' && bits == 64 && opt", # Bug 1591590
]

View file

@ -34,14 +34,12 @@ support-files = [
["browser_jsterm_add_edited_input_to_history.js"]
["browser_jsterm_autocomplete-properties-with-non-alphanumeric-names.js"]
skip-if = ["win11_2009 && debug && bits == 32"] # Bug 1620856
["browser_jsterm_autocomplete_accept_no_scroll.js"]
["browser_jsterm_autocomplete_array_no_index.js"]
["browser_jsterm_autocomplete_arrow_keys.js"]
skip-if = ["win11_2009 && debug && bits == 32"] # Bug 1620856
["browser_jsterm_autocomplete_await.js"]
@ -276,7 +274,7 @@ fail-if = ["a11y_checks"] # Bug 1849028
["browser_jsterm_screenshot_command_user.js"]
["browser_jsterm_screenshot_command_warnings.js"]
skip-if = ["os == 'linux' && bits == 64 && !debug"] # Bug 1701439
skip-if = ["os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt"] # Bug 1701439
["browser_jsterm_selfxss.js"]

View file

@ -291,7 +291,7 @@ skip-if = [
"tsan", # Bug 1767724
"release_or_beta", # requires dom.postMessage.sharedArrayBuffer.bypassCOOP_COEP.insecure.enabled
"os == 'linux'", # Bug 1767724
"apple_catalina && debug", # Bug 1767724
"os == 'mac' && os_version == '10.15' && processor == 'x86_64' && debug", # Bug 1767724
]
["browser_webconsole_console_profile_unavailable.js"]
@ -324,7 +324,7 @@ skip-if = [
["browser_webconsole_context_menu_copy_link_location.js"]
https_first_disabled = true
skip-if = [
"os == 'linux'", # bug 1473120
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # bug 1473120
"http3", # Bug 1829298
"http2",
]
@ -335,7 +335,7 @@ skip-if = [
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
["browser_webconsole_context_menu_copy_object.js"]
skip-if = ["apple_catalina"] # Bug 1713158
skip-if = ["os == 'mac' && os_version == '10.15' && processor == 'x86_64'"] # Bug 1713158
["browser_webconsole_context_menu_export_console_output.js"]
@ -351,7 +351,7 @@ skip-if = [
["browser_webconsole_context_menu_reveal_in_inspector.js"]
["browser_webconsole_context_menu_store_as_global.js"]
skip-if = ["apple_catalina"] # Bug 1713158
skip-if = ["os == 'mac' && os_version == '10.15' && processor == 'x86_64'"] # Bug 1713158
["browser_webconsole_cors_errors.js"]
https_first_disabled = true
@ -414,8 +414,8 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_webconsole_eval_in_debugger_stackframe2.js"]
skip-if = [
"!debug && os == 'linux'", #Bug 1598205
"!debug && os == 'win'", #Bug 1598205
"os == 'linux' && os_version == '18.04' && processor == 'x86_64' && opt", #Bug 1598205
"os == 'win' && os_version == '11.2009' && processor == 'x86_64' && opt", #Bug 1598205
]
["browser_webconsole_eval_sources.js"]
@ -538,7 +538,7 @@ skip-if = ["a11y_checks"] # Bug 1849028 and 1849179 for causing crashes
["browser_webconsole_network_messages_expand_before_updates.js"]
skip-if = [
"os == 'win'", # Bug 1689101
"os == 'linux'", # Bug 1689101
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1689101
]
["browser_webconsole_network_messages_html_preview.js"]
@ -577,7 +577,7 @@ fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and
["browser_webconsole_object_ctrl_click.js"]
fail-if = ["a11y_checks"] # Bug 1849028 clicked element may not be focusable and/or labeled
skip-if = ["apple_catalina"] # Bug 1713158
skip-if = ["os == 'mac' && os_version == '10.15' && processor == 'x86_64'"] # Bug 1713158
["browser_webconsole_object_in_sidebar_keyboard_nav.js"]

View file

@ -55,11 +55,10 @@ support-files = [
["browser_resources_css_messages.js"]
["browser_resources_css_registered_properties.js"]
skip-if = ["!fission"]
["browser_resources_document_events.js"]
skip-if = [
"os == 'linux' && bits == 64", # Bug 1715878
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1715878
]
["browser_resources_error_messages.js"]
@ -94,9 +93,9 @@ skip-if = [
["browser_resources_sources.js"]
skip-if = [
"os == 'linux' && bits == 64", # Bug 1744565
"os == 'linux' && os_version == '18.04' && processor == 'x86_64'", # Bug 1744565
"win11_2009", # Bug 1767772
"apple_catalina", # Bug 1767772
"os == 'mac' && os_version == '10.15' && processor == 'x86_64'", # Bug 1767772
]
["browser_resources_stylesheets.js"]

View file

@ -516,7 +516,7 @@ Permissions* Navigator::GetPermissions(ErrorResult& aRv) {
}
if (!mPermissions) {
mPermissions = new Permissions(mWindow->AsGlobal());
mPermissions = new Permissions(mWindow);
}
return mPermissions;

View file

@ -98,8 +98,8 @@ LOCAL_INCLUDES += [
"/layout/xul/tree",
"/media/webrtc/",
"/netwerk/base/",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
LOCAL_INCLUDES += ["/third_party/msgpack/include"]

View file

@ -47,11 +47,25 @@ BackingTexture::BackingTexture(const IntSize& aSize, SurfaceFormat aFormat,
const RefPtr<WebGLTexture>& aTexture)
: mSize(aSize), mFormat(aFormat), mTexture(aTexture) {}
#ifdef XP_WIN
// Work around buggy ANGLE/D3D drivers that may copy blocks of pixels outside
// the row length. Extra space is reserved at the end of each row up to stride
// alignment. This does not affect standalone textures.
static const Etagere::AllocatorOptions kR8AllocatorOptions = {16, 1, 1, 0};
#endif
SharedTexture::SharedTexture(const IntSize& aSize, SurfaceFormat aFormat,
const RefPtr<WebGLTexture>& aTexture)
: BackingTexture(aSize, aFormat, aTexture),
mAtlasAllocator(
Etagere::etagere_atlas_allocator_new(aSize.width, aSize.height)) {}
#ifdef XP_WIN
aFormat == SurfaceFormat::A8
? Etagere::etagere_atlas_allocator_with_options(
aSize.width, aSize.height, &kR8AllocatorOptions)
:
#endif
Etagere::etagere_atlas_allocator_new(aSize.width, aSize.height)) {
}
SharedTexture::~SharedTexture() {
if (mAtlasAllocator) {

View file

@ -20,9 +20,6 @@ support-files = [
["browser_bug1539497.js"]
["browser_dragdrop_protected_diff_origin.js"]
skip-if = [
"os == 'mac'", # Bug 1923546 - temp disabled due to permafails until a fix in place
]
["browser_dragdrop_protected_same_origin.js"]

View file

@ -7156,12 +7156,17 @@ void HTMLMediaElement::MakeAssociationWithCDMResolved() {
mSetMediaKeysDOMPromise = nullptr;
if (profiler_is_collecting_markers()) {
nsString keySystem;
mMediaKeys->GetKeySystem(keySystem);
profiler_add_marker(nsPrintfCString("%p:mozcdmresolved", this),
geckoprofiler::category::MEDIA_PLAYBACK, {},
CDMResolvedMarker{}, keySystem,
mMediaKeys->GetMediaKeySystemConfigurationString());
if (mMediaKeys) {
nsString keySystem;
mMediaKeys->GetKeySystem(keySystem);
profiler_add_marker(nsPrintfCString("%p:mozcdmresolved", this),
geckoprofiler::category::MEDIA_PLAYBACK, {},
CDMResolvedMarker{}, keySystem,
mMediaKeys->GetMediaKeySystemConfigurationString());
} else {
nsPrintfCString markerName{"%p:mozremovemediakey", this};
PROFILER_MARKER_UNTYPED(markerName, MEDIA_PLAYBACK);
}
}
}

View file

@ -237,8 +237,8 @@ LOCAL_INCLUDES += [
"/layout/xul",
"/netwerk/base",
"/parser/htmlparser",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
FINAL_LIBRARY = "xul"

View file

@ -24,8 +24,8 @@ LOCAL_INCLUDES += [
"/dom/media/webrtc/transportbridge",
"/ipc/chromium/src",
"/media/webrtc/",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
if CONFIG["MOZ_WEBRTC"]:

View file

@ -15,8 +15,8 @@ LOCAL_INCLUDES += [
"/dom/media/systemservices",
"/dom/media/webrtc",
"/dom/media/webrtc/common",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
UNIFIED_SOURCES += [

View file

@ -98,7 +98,7 @@ AudioSink::~AudioSink() {
}
nsresult AudioSink::InitializeAudioStream(
const PlaybackParams& aParams, const RefPtr<AudioDeviceInfo>& aAudioDevice,
const RefPtr<AudioDeviceInfo>& aAudioDevice,
AudioSink::InitializationType aInitializationType) {
if (aInitializationType == AudioSink::InitializationType::UNMUTING) {
// Consider the stream to be audible immediately, before initialization
@ -133,19 +133,19 @@ nsresult AudioSink::InitializeAudioStream(
return rv;
}
return NS_OK;
}
RefPtr<MediaSink::EndedPromise> AudioSink::Start(
const PlaybackParams& aParams, const media::TimeUnit& aStartTime) {
MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn());
// Set playback params before calling Start() so they can take effect
// as soon as the 1st DataCallback of the AudioStream fires.
mAudioStream->SetVolume(aParams.mVolume);
mAudioStream->SetPlaybackRate(aParams.mPlaybackRate);
mAudioStream->SetPreservesPitch(aParams.mPreservesPitch);
return NS_OK;
}
RefPtr<MediaSink::EndedPromise> AudioSink::Start(
const media::TimeUnit& aStartTime) {
MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn());
mAudioQueueListener = mAudioQueue.PushEvent().Connect(
mOwnerThread, this, &AudioSink::OnAudioPushed);
mAudioQueueFinishListener = mAudioQueue.FinishEvent().Connect(

View file

@ -47,13 +47,13 @@ class AudioSink : private AudioStream::DataSource {
~AudioSink();
// Allocate and initialize mAudioStream. Returns NS_OK on success.
nsresult InitializeAudioStream(const PlaybackParams& aParams,
const RefPtr<AudioDeviceInfo>& aAudioDevice,
nsresult InitializeAudioStream(const RefPtr<AudioDeviceInfo>& aAudioDevice,
InitializationType aInitializationType);
// Start audio playback. aStartTime is compared with MediaData::mTime to
// identify the first audio frame to be played.
RefPtr<MediaSink::EndedPromise> Start(const media::TimeUnit& aStartTime);
RefPtr<MediaSink::EndedPromise> Start(const PlaybackParams& aParams,
const media::TimeUnit& aStartTime);
/*
* All public functions are not thread-safe.

View file

@ -332,8 +332,8 @@ void AudioSinkWrapper::StartAudioSink(UniquePtr<AudioSink> aAudioSink,
AssertOwnerThread();
MOZ_ASSERT(!mAudioSink);
mAudioSink = std::move(aAudioSink);
mAudioSink->Start(aStartTime)
->Then(mOwnerThread.get(), __func__, this,
mAudioSink->Start(mParams, aStartTime)
->Then(mOwnerThread.GetEventTarget(), __func__, this,
&AudioSinkWrapper::OnAudioEnded)
->Track(mAudioSinkEndedRequest);
}
@ -370,37 +370,36 @@ RefPtr<GenericPromise> AudioSinkWrapper::MaybeAsyncCreateAudioSink(
++mAsyncCreateCount;
using Promise =
MozPromise<UniquePtr<AudioSink>, nsresult, /* IsExclusive = */ true>;
return InvokeAsync(mAsyncInitTaskQueue,
"MaybeAsyncCreateAudioSink (Async part: initialization)",
[self = RefPtr<AudioSinkWrapper>(this),
audioSink{std::move(audioSink)},
audioDevice = mAudioDevice, this]() mutable {
if (!audioSink || !mAsyncInitTaskQueue->IsEmpty()) {
// Either an AudioSink is not required or there's a
// pending task to init an AudioSink with a possibly
// different device.
return Promise::CreateAndResolve(nullptr, __func__);
}
return InvokeAsync(
mAsyncInitTaskQueue,
"MaybeAsyncCreateAudioSink (Async part: initialization)",
[self = RefPtr<AudioSinkWrapper>(this),
audioSink{std::move(audioSink)}, audioDevice = mAudioDevice,
this]() mutable {
if (!audioSink || !mAsyncInitTaskQueue->IsEmpty()) {
// Either an AudioSink is not required or there's a
// pending task to init an AudioSink with a possibly
// different device.
return Promise::CreateAndResolve(nullptr, __func__);
}
LOG("AudioSink initialization on background thread");
// This can take about 200ms, e.g. on Windows, we don't
// want to do it on the MDSM thread, because it would
// make the clock not update for that amount of time, and
// the video would therefore not update. The Start() call
// is very cheap on the other hand, we can do it from the
// MDSM thread.
nsresult rv = audioSink->InitializeAudioStream(
mParams, audioDevice,
AudioSink::InitializationType::UNMUTING);
if (NS_FAILED(rv)) {
LOG("Async AudioSink initialization failed");
return Promise::CreateAndReject(rv, __func__);
}
return Promise::CreateAndResolve(std::move(audioSink),
__func__);
})
LOG("AudioSink initialization on background thread");
// This can take about 200ms, e.g. on Windows, we don't
// want to do it on the MDSM thread, because it would
// make the clock not update for that amount of time, and
// the video would therefore not update. The Start() call
// is very cheap on the other hand, we can do it from the
// MDSM thread.
nsresult rv = audioSink->InitializeAudioStream(
audioDevice, AudioSink::InitializationType::UNMUTING);
if (NS_FAILED(rv)) {
LOG("Async AudioSink initialization failed");
return Promise::CreateAndReject(rv, __func__);
}
return Promise::CreateAndResolve(std::move(audioSink), __func__);
})
->Then(
mOwnerThread,
mOwnerThread.GetEventTarget(),
"MaybeAsyncCreateAudioSink (Async part: start from MDSM thread)",
[self = RefPtr<AudioSinkWrapper>(this), audioDevice = mAudioDevice,
this](Promise::ResolveOrRejectValue&& aValue) mutable {
@ -478,7 +477,7 @@ nsresult AudioSinkWrapper::SyncCreateAudioSink(const TimeUnit& aStartTime) {
UniquePtr<AudioSink> audioSink = mSinkCreator();
nsresult rv = audioSink->InitializeAudioStream(
mParams, mAudioDevice, AudioSink::InitializationType::INITIAL);
mAudioDevice, AudioSink::InitializationType::INITIAL);
if (NS_FAILED(rv)) {
LOG("Sync AudioSinkWrapper initialization failed");
// If a specific device has been specified through setSinkId()

View file

@ -8,6 +8,7 @@
#define AudioSinkWrapper_h_
#include "mozilla/AbstractThread.h"
#include "mozilla/EventTargetCapability.h"
#include "mozilla/RefPtr.h"
#include "mozilla/TimeStamp.h"
#include "mozilla/UniquePtr.h"
@ -85,8 +86,8 @@ class AudioSinkWrapper : public MediaSink {
void OnMuted(bool aMuted);
virtual ~AudioSinkWrapper();
void AssertOwnerThread() const {
MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn());
void AssertOwnerThread() const MOZ_ASSERT_CAPABILITY(mOwnerThread) {
mOwnerThread.AssertOnCurrentThread();
}
bool NeedAudioSink();
@ -121,7 +122,7 @@ class AudioSinkWrapper : public MediaSink {
bool IsAudioSourceEnded(const MediaInfo& aInfo) const;
const RefPtr<AbstractThread> mOwnerThread;
const EventTargetCapability<AbstractThread> mOwnerThread;
const RefPtr<TaskQueue> mAsyncInitTaskQueue;
SinkCreator mSinkCreator;
UniquePtr<AudioSink> mAudioSink;
@ -133,7 +134,7 @@ class AudioSinkWrapper : public MediaSink {
MozPromiseHolder<EndedPromise> mEndedPromiseHolder;
// true between Start() and Stop()
bool mIsStarted = false;
PlaybackParams mParams;
PlaybackParams MOZ_GUARDED_BY(mOwnerThread) mParams;
// mClockStartTime is null before Start(), after Stop(), and between
// SetPlaying(false) and SetPlaying(true). When the system time is used for
// the clock, this is the time corresponding to mPositionAtClockStart. When

View file

@ -372,8 +372,8 @@ LOCAL_INCLUDES += [
if CONFIG["MOZ_WEBRTC"]:
LOCAL_INCLUDES += [
"/dom/media/webrtc/common",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
DEFINES["MOZILLA_INTERNAL_API"] = True

View file

@ -334,7 +334,7 @@ int CamerasChild::AllocateCapture(CaptureEngine aCapEngine,
LOG(("%s", __PRETTY_FUNCTION__));
nsCString unique_id(unique_idUTF8);
nsCOMPtr<nsIRunnable> runnable =
mozilla::NewRunnableMethod<CaptureEngine, nsCString, const uint64_t&>(
mozilla::NewRunnableMethod<CaptureEngine, nsCString, uint64_t>(
"camera::PCamerasChild::SendAllocateCapture", this,
&CamerasChild::SendAllocateCapture, aCapEngine, unique_id, aWindowID);
LockAndDispatch<> dispatcher(this, __func__, runnable, -1, mReplyInteger);

View file

@ -22,8 +22,8 @@ if CONFIG["MOZ_WEBRTC"]:
"/dom/media/webrtc",
"/media/libyuv/libyuv/include",
"/mfbt",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
"/tools/profiler/public",
]

View file

@ -9,8 +9,8 @@ EXPORTS.mozilla.dom += ["CandidateInfo.h"]
LOCAL_INCLUDES += [
"/dom/media/webrtc/transport/third_party/nrappkit/src/util/libekr",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
UNIFIED_SOURCES += [

View file

@ -603,31 +603,30 @@ RefPtr<DtlsIdentity> PeerConnectionImpl::Identity() const {
class CompareCodecPriority {
public:
void SetPreferredCodec(int32_t preferredCodec) {
// This pref really ought to be a string, preferably something like
// "H264" or "VP8" instead of a payload type.
// Bug 1101259.
std::ostringstream os;
os << preferredCodec;
mPreferredCodec = os.str();
void SetPreferredCodec(const nsCString& preferredCodec) {
mPreferredCodec = preferredCodec;
}
bool operator()(const UniquePtr<JsepCodecDescription>& lhs,
const UniquePtr<JsepCodecDescription>& rhs) const {
if (!mPreferredCodec.empty() && lhs->mDefaultPt == mPreferredCodec &&
rhs->mDefaultPt != mPreferredCodec) {
return true;
// Do we have a preferred codec?
if (!mPreferredCodec.IsEmpty()) {
const bool lhsMatches = mPreferredCodec.EqualsIgnoreCase(lhs->mName) ||
mPreferredCodec.EqualsIgnoreCase(lhs->mDefaultPt);
const bool rhsMatches = mPreferredCodec.EqualsIgnoreCase(rhs->mName) ||
mPreferredCodec.EqualsIgnoreCase(rhs->mDefaultPt);
// If the only the left side matches, prefer it
if (lhsMatches && !rhsMatches) {
return true;
}
}
if (lhs->mStronglyPreferred && !rhs->mStronglyPreferred) {
return true;
}
return false;
// If only the left side is strongly preferred, prefer it
return (lhs->mStronglyPreferred && !rhs->mStronglyPreferred);
}
private:
std::string mPreferredCodec;
// The preferred codec name or PT number
nsCString mPreferredCodec;
};
class ConfigureCodec {
@ -811,15 +810,7 @@ nsresult PeerConnectionImpl::ConfigureJsepSessionCodecs() {
// We use this to sort the list of codecs once everything is configured
CompareCodecPriority comparator;
// Sort by priority
int32_t preferredCodec = 0;
branch->GetIntPref("media.navigator.video.preferred_codec", &preferredCodec);
if (preferredCodec) {
comparator.SetPreferredCodec(preferredCodec);
}
mJsepSession->SortCodecs(comparator);
return NS_OK;
}

View file

@ -13,9 +13,9 @@ LOCAL_INCLUDES += [
"/ipc/chromium/src",
"/media/webrtc",
"/netwerk/dns", # For nsDNSService2.h
"/third_party/abseil-cpp",
"/third_party/libsrtp/src/include",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
UNIFIED_SOURCES += [

View file

@ -8,8 +8,8 @@ include("/dom/media/webrtc/third_party_build/webrtc.mozbuild")
LOCAL_INCLUDES += [
"/dom/media/webrtc",
"/media/webrtc",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
"/third_party/sipcc",
]

View file

@ -13,9 +13,9 @@ LOCAL_INCLUDES += [
"/ipc/chromium/src",
"/media/libyuv/libyuv/include",
"/media/webrtc",
"/third_party/abseil-cpp",
"/third_party/libsrtp/src/include",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
UNIFIED_SOURCES += [

View file

@ -68,8 +68,8 @@ if CONFIG["MOZ_WEBRTC"]:
"/dom/media/webrtc/common",
"/dom/media/webrtc/common/browser_logging",
"/media/libyuv/libyuv/include",
"/third_party/abseil-cpp",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
if CONFIG["MOZ_WEBRTC_SIGNALING"]:
@ -81,6 +81,7 @@ if CONFIG["MOZ_WEBRTC_SIGNALING"]:
"sdp",
"transportbridge",
"/third_party/libwebrtc",
"/third_party/abseil-cpp",
]
if CONFIG["MOZ_WIDGET_TOOLKIT"] == "gtk":

View file

@ -8,5 +8,5 @@ license = "MPL-2.0"
[dependencies]
libc = "^0.2.0"
log = "0.4"
rsdparsa = {package = "webrtc-sdp", version = "0.3.11"}
rsdparsa = {package = "webrtc-sdp", version = "0.3.13"}
nserror = { path = "../../../../../xpcom/rust/nserror" }

View file

@ -0,0 +1,24 @@
{
"build_root_dir": "third_party",
"target_dir": "abseil-cpp",
"preprocessing_script": "dom/media/webrtc/third_party_build/gn-configs/abseil_preprocessor.py",
"moz_build_flag": "build_mozilla_absl",
"gn_target": "//:absl",
"gn_sandbox_variables": {
"COMPILE_FLAGS": {
"WARNINGS_AS_ERRORS": []
},
"FINAL_LIBRARY": "xul"
},
"mozilla_flags": ["-fobjc-arc", "-mavx2", "-mfma", "-mfpu=neon", "-msse2"],
"write_mozbuild_variables": {
"INCLUDE_TK_CFLAGS_DIRS": [],
"INCLUDE_SYSTEM_LIBVPX_HANDLING": []
},
"non_unified_sources": [
"third_party/abseil-cpp/absl/strings/numbers.cc",
"third_party/abseil-cpp/absl/synchronization/blocking_counter.cc",
"third_party/abseil-cpp/absl/time/internal/cctz/src/time_zone_posix.cc",
"third_party/abseil-cpp/absl/time/time.cc"
]
}

View file

@ -0,0 +1,14 @@
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at https://mozilla.org/MPL/2.0/.
def main(gn_config_file):
target_dir = "abseil-cpp"
raw_file_contents = ""
with open(gn_config_file, "r") as fh:
raw_file_contents = fh.read()
raw_file_contents = raw_file_contents.replace(f"{target_dir}/", "")
raw_file_contents = raw_file_contents.replace(f"{target_dir}:", ":")
with open(gn_config_file, "w") as fh:
fh.write(raw_file_contents)

View file

@ -1,5 +1,8 @@
{
"target_dir": "third_party/libwebrtc",
"build_root_dir": "third_party",
"target_dir": "libwebrtc",
"preprocessing_script": "dom/media/webrtc/third_party_build/gn-configs/webrtc_preprocessor.py",
"moz_build_flag": "build_mozilla_webrtc",
"gn_target": "//:webrtc",
"gn_sandbox_variables": {
"COMPILE_FLAGS": {

View file

@ -0,0 +1,14 @@
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at https://mozilla.org/MPL/2.0/.
def main(gn_config_file):
target_dir = "libwebrtc"
raw_file_contents = ""
with open(gn_config_file, "r") as fh:
raw_file_contents = fh.read()
raw_file_contents = raw_file_contents.replace(f"{target_dir}/", "")
raw_file_contents = raw_file_contents.replace(f"{target_dir}:", ":")
with open(gn_config_file, "w") as fh:
fh.write(raw_file_contents)

View file

@ -12,10 +12,10 @@ LOCAL_INCLUDES += [
"/ipc/chromium/src",
"/media/libyuv/libyuv/include",
"/media/webrtc",
"/third_party/abseil-cpp",
"/third_party/libsrtp/src/crypto/include",
"/third_party/libsrtp/src/include",
"/third_party/libwebrtc",
"/third_party/libwebrtc/third_party/abseil-cpp",
]
UNIFIED_SOURCES += [

View file

@ -11,9 +11,9 @@
namespace mozilla::dom {
MidiPermissionStatus::MidiPermissionStatus(nsIGlobalObject* aGlobal,
MidiPermissionStatus::MidiPermissionStatus(nsPIDOMWindowInner* aWindow,
bool aSysex)
: PermissionStatus(aGlobal, PermissionName::Midi), mSysex(aSysex) {}
: PermissionStatus(aWindow, PermissionName::Midi), mSysex(aSysex) {}
nsLiteralCString MidiPermissionStatus::GetPermissionType() const {
return mSysex ? "midi-sysex"_ns : "midi"_ns;

View file

@ -13,7 +13,7 @@ namespace mozilla::dom {
class MidiPermissionStatus final : public PermissionStatus {
public:
MidiPermissionStatus(nsIGlobalObject* aGlobal, bool aSysex);
MidiPermissionStatus(nsPIDOMWindowInner* aWindow, bool aSysex);
private:
~MidiPermissionStatus() {}

View file

@ -6,11 +6,12 @@
#include "PermissionObserver.h"
#include "mozilla/dom/PermissionStatus.h"
#include "mozilla/dom/WindowGlobalChild.h"
#include "mozilla/Services.h"
#include "mozilla/UniquePtr.h"
#include "nsIObserverService.h"
#include "nsIPermission.h"
#include "PermissionStatusSink.h"
#include "PermissionUtils.h"
namespace mozilla::dom {
@ -21,13 +22,9 @@ PermissionObserver* gInstance = nullptr;
NS_IMPL_ISUPPORTS(PermissionObserver, nsIObserver, nsISupportsWeakReference)
PermissionObserver::PermissionObserver() {
MOZ_ASSERT_DEBUG_OR_FUZZING(NS_IsMainThread());
MOZ_ASSERT(!gInstance);
}
PermissionObserver::PermissionObserver() { MOZ_ASSERT(!gInstance); }
PermissionObserver::~PermissionObserver() {
MOZ_ASSERT_DEBUG_OR_FUZZING(NS_IsMainThread());
MOZ_ASSERT(mSinks.IsEmpty());
MOZ_ASSERT(gInstance == this);
@ -36,8 +33,6 @@ PermissionObserver::~PermissionObserver() {
/* static */
already_AddRefed<PermissionObserver> PermissionObserver::GetInstance() {
MOZ_ASSERT_DEBUG_OR_FUZZING(NS_IsMainThread());
RefPtr<PermissionObserver> instance = gInstance;
if (!instance) {
instance = new PermissionObserver();
@ -63,16 +58,14 @@ already_AddRefed<PermissionObserver> PermissionObserver::GetInstance() {
return instance.forget();
}
void PermissionObserver::AddSink(PermissionStatusSink* aSink) {
MOZ_ASSERT_DEBUG_OR_FUZZING(NS_IsMainThread());
void PermissionObserver::AddSink(PermissionStatus* aSink) {
MOZ_ASSERT(aSink);
MOZ_ASSERT(!mSinks.Contains(aSink));
mSinks.AppendElement(aSink);
}
void PermissionObserver::RemoveSink(PermissionStatusSink* aSink) {
MOZ_ASSERT_DEBUG_OR_FUZZING(NS_IsMainThread());
void PermissionObserver::RemoveSink(PermissionStatus* aSink) {
MOZ_ASSERT(aSink);
MOZ_ASSERT(mSinks.Contains(aSink));
@ -82,7 +75,6 @@ void PermissionObserver::RemoveSink(PermissionStatusSink* aSink) {
NS_IMETHODIMP
PermissionObserver::Observe(nsISupports* aSubject, const char* aTopic,
const char16_t* aData) {
MOZ_ASSERT_DEBUG_OR_FUZZING(NS_IsMainThread());
MOZ_ASSERT(!strcmp(aTopic, "perm-changed") ||
!strcmp(aTopic, "perm-changed-notify-only"));
@ -110,15 +102,15 @@ PermissionObserver::Observe(nsISupports* aSubject, const char* aTopic,
Maybe<PermissionName> permission = TypeToPermissionName(type);
if (permission) {
for (PermissionStatusSink* sink : mSinks) {
if (sink->Name() != permission.value()) {
for (auto* sink : mSinks) {
if (sink->mName != permission.value()) {
continue;
}
// Check for permissions that are changed for this sink's principal
// via the "perm-changed" notification. These permissions affect
// the window the sink (PermissionStatus) is held in directly.
if (perm && sink->MaybeUpdatedByOnMainThread(perm)) {
sink->PermissionChangedOnMainThread();
if (perm && sink->MaybeUpdatedBy(perm)) {
sink->PermissionChanged();
}
// Check for permissions that are changed for this sink's principal
// via the "perm-changed-notify-only" notification. These permissions
@ -127,9 +119,8 @@ PermissionObserver::Observe(nsISupports* aSubject, const char* aTopic,
// example, a "3rdPartyFrameStorage^https://example.com" permission would
// return true on these checks where sink is in a window that is same-site
// with https://example.com.
if (innerWindow &&
sink->MaybeUpdatedByNotifyOnlyOnMainThread(innerWindow)) {
sink->PermissionChangedOnMainThread();
if (innerWindow && sink->MaybeUpdatedByNotifyOnly(innerWindow)) {
sink->PermissionChanged();
}
}
}

View file

@ -7,13 +7,16 @@
#ifndef mozilla_dom_PermissionObserver_h_
#define mozilla_dom_PermissionObserver_h_
#include "mozilla/dom/PermissionsBinding.h"
#include "nsIObserver.h"
#include "nsIPrincipal.h"
#include "nsTArray.h"
#include "nsWeakReference.h"
namespace mozilla::dom {
class PermissionStatusSink;
class PermissionStatus;
// Singleton that watches for perm-changed notifications in order to notify
// PermissionStatus objects.
@ -25,14 +28,14 @@ class PermissionObserver final : public nsIObserver,
static already_AddRefed<PermissionObserver> GetInstance();
void AddSink(PermissionStatusSink* aSink);
void RemoveSink(PermissionStatusSink* aSink);
void AddSink(PermissionStatus* aObs);
void RemoveSink(PermissionStatus* aObs);
private:
PermissionObserver();
virtual ~PermissionObserver();
nsTArray<RefPtr<PermissionStatusSink>> mSinks;
nsTArray<PermissionStatus*> mSinks;
};
} // namespace mozilla::dom

View file

@ -5,20 +5,21 @@
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "mozilla/dom/PermissionStatus.h"
#include "mozilla/PermissionDelegateHandler.h"
#include "mozilla/AsyncEventDispatcher.h"
#include "mozilla/Permission.h"
#include "mozilla/Services.h"
#include "nsIPermissionManager.h"
#include "PermissionObserver.h"
#include "PermissionUtils.h"
#include "PermissionStatusSink.h"
#include "nsGlobalWindowInner.h"
namespace mozilla::dom {
PermissionStatus::PermissionStatus(nsIGlobalObject* aGlobal,
PermissionStatus::PermissionStatus(nsPIDOMWindowInner* aWindow,
PermissionName aName)
: DOMEventTargetHelper(aGlobal),
: DOMEventTargetHelper(aWindow),
mName(aName),
mState(PermissionState::Denied) {
KeepAliveIfHasListenersFor(nsGkAtoms::onchange);
@ -27,26 +28,24 @@ PermissionStatus::PermissionStatus(nsIGlobalObject* aGlobal,
// https://w3c.github.io/permissions/#onchange-attribute and
// https://w3c.github.io/permissions/#query-method
RefPtr<PermissionStatus::SimplePromise> PermissionStatus::Init() {
mSink = CreateSink();
MOZ_ASSERT(mSink);
// Covers the onchange part
// Whenever the user agent is aware that the state of a PermissionStatus
// instance status has changed: ...
// (The observer calls PermissionChanged() to do the steps)
mObserver = PermissionObserver::GetInstance();
if (NS_WARN_IF(!mObserver)) {
return SimplePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
return mSink->Init()->Then(
GetCurrentSerialEventTarget(), __func__,
[self = RefPtr(this)](const PermissionStatusSink::PermissionStatePromise::
ResolveOrRejectValue& aResult) {
if (aResult.IsResolve()) {
self->mState = self->ComputeStateFromAction(aResult.ResolveValue());
return SimplePromise::CreateAndResolve(NS_OK, __func__);
}
mObserver->AddSink(this);
return SimplePromise::CreateAndReject(aResult.RejectValue(), __func__);
});
// Covers the query part (Step 8.2 - 8.4)
return UpdateState();
}
PermissionStatus::~PermissionStatus() {
if (mSink) {
mSink->Disentangle();
mSink = nullptr;
if (mObserver) {
mObserver->RemoveSink(this);
}
}
@ -59,28 +58,111 @@ nsLiteralCString PermissionStatus::GetPermissionType() const {
return PermissionNameToType(mName);
}
// https://w3c.github.io/permissions/#dfn-permissionstatus-update-steps
void PermissionStatus::PermissionChanged(uint32_t aAction) {
PermissionState newState = ComputeStateFromAction(aAction);
if (mState == newState) {
return;
// Covers the calling part of "permission query algorithm" of query() method and
// update steps, which calls
// https://w3c.github.io/permissions/#dfn-default-permission-query-algorithm
// and then https://w3c.github.io/permissions/#dfn-permission-state
RefPtr<PermissionStatus::SimplePromise> PermissionStatus::UpdateState() {
// Step 1: If settings wasn't passed, set it to the current settings object.
// Step 2: If settings is a non-secure context, return "denied".
// XXX(krosylight): No such steps here, and no WPT coverage?
// The permission handler covers the rest of the steps, although the model
// does not exactly match what the spec has. (Not passing "permission key" for
// example)
RefPtr<nsGlobalWindowInner> window = GetOwnerWindow();
if (NS_WARN_IF(!window)) {
return SimplePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
mState = newState;
RefPtr<Document> document = window->GetExtantDoc();
if (NS_WARN_IF(!document)) {
return SimplePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
// Step 4: Queue a task on the permissions task source to fire an
// event named change at status.
RefPtr<AsyncEventDispatcher> eventDispatcher =
new AsyncEventDispatcher(this, u"change"_ns, CanBubble::eNo);
eventDispatcher->PostDOMEvent();
uint32_t action = nsIPermissionManager::DENY_ACTION;
PermissionDelegateHandler* permissionHandler =
document->GetPermissionDelegateHandler();
if (NS_WARN_IF(!permissionHandler)) {
return SimplePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
nsresult rv = permissionHandler->GetPermissionForPermissionsAPI(
GetPermissionType(), &action);
if (NS_WARN_IF(NS_FAILED(rv))) {
return SimplePromise::CreateAndReject(rv, __func__);
}
mState = ActionToPermissionState(action, mName, *document);
return SimplePromise::CreateAndResolve(NS_OK, __func__);
}
bool PermissionStatus::MaybeUpdatedBy(nsIPermission* aPermission) const {
NS_ENSURE_TRUE(aPermission, false);
RefPtr<nsGlobalWindowInner> window = GetOwnerWindow();
if (NS_WARN_IF(!window)) {
return false;
}
Document* doc = window->GetExtantDoc();
if (NS_WARN_IF(!doc)) {
return false;
}
nsCOMPtr<nsIPrincipal> principal =
Permission::ClonePrincipalForPermission(doc->NodePrincipal());
NS_ENSURE_TRUE(principal, false);
nsCOMPtr<nsIPrincipal> permissionPrincipal;
aPermission->GetPrincipal(getter_AddRefs(permissionPrincipal));
if (!permissionPrincipal) {
return false;
}
return permissionPrincipal->Equals(principal);
}
bool PermissionStatus::MaybeUpdatedByNotifyOnly(
nsPIDOMWindowInner* aInnerWindow) const {
return false;
}
// https://w3c.github.io/permissions/#dfn-permissionstatus-update-steps
void PermissionStatus::PermissionChanged() {
auto oldState = mState;
RefPtr<PermissionStatus> self(this);
// Step 1: If this's relevant global object is a Window object, then:
// Step 1.1: Let document be status's relevant global object's associated
// Document.
// Step 1.2: If document is null or document is not fully active,
// terminate this algorithm.
// TODO(krosylight): WPT /permissions/non-fully-active.https.html fails
// because we don't do this. See bug 1876470.
// Step 2 - 3 is covered by UpdateState()
UpdateState()->Then(
GetMainThreadSerialEventTarget(), __func__,
[self, oldState]() {
if (self->mState != oldState) {
// Step 4: Queue a task on the permissions task source to fire an
// event named change at status.
RefPtr<AsyncEventDispatcher> eventDispatcher =
new AsyncEventDispatcher(self.get(), u"change"_ns,
CanBubble::eNo);
eventDispatcher->PostDOMEvent();
}
},
[]() {
});
}
void PermissionStatus::DisconnectFromOwner() {
IgnoreKeepAliveIfHasListenersFor(nsGkAtoms::onchange);
if (mSink) {
mSink->Disentangle();
mSink = nullptr;
if (mObserver) {
mObserver->RemoveSink(this);
mObserver = nullptr;
}
DOMEventTargetHelper::DisconnectFromOwner();
@ -90,19 +172,4 @@ void PermissionStatus::GetType(nsACString& aName) const {
aName.Assign(GetPermissionType());
}
already_AddRefed<PermissionStatusSink> PermissionStatus::CreateSink() {
RefPtr<PermissionStatusSink> sink =
new PermissionStatusSink(this, mName, GetPermissionType());
return sink.forget();
}
PermissionState PermissionStatus::ComputeStateFromAction(uint32_t aAction) {
nsCOMPtr<nsIGlobalObject> global = GetOwnerGlobal();
if (NS_WARN_IF(!global)) {
return PermissionState::Denied;
}
return ActionToPermissionState(aAction, mName, global);
}
} // namespace mozilla::dom

View file

@ -11,18 +11,19 @@
#include "mozilla/dom/PermissionStatusBinding.h"
#include "mozilla/DOMEventTargetHelper.h"
#include "mozilla/MozPromise.h"
#include "nsIPermission.h"
namespace mozilla::dom {
class PermissionStatusSink;
class PermissionObserver;
class PermissionStatus : public DOMEventTargetHelper {
friend class PermissionStatusSink;
friend class PermissionObserver;
public:
using SimplePromise = MozPromise<nsresult, nsresult, true>;
PermissionStatus(nsIGlobalObject* aGlobal, PermissionName aName);
PermissionStatus(nsPIDOMWindowInner* aWindow, PermissionName aName);
JSObject* WrapObject(JSContext* aCx,
JS::Handle<JSObject*> aGivenProto) override;
@ -56,14 +57,23 @@ class PermissionStatus : public DOMEventTargetHelper {
virtual nsLiteralCString GetPermissionType() const;
private:
virtual already_AddRefed<PermissionStatusSink> CreateSink();
virtual RefPtr<SimplePromise> UpdateState();
void PermissionChanged(uint32_t aAction);
// These functions should be called when an permission is updated which may
// change the state of this PermissionStatus. MaybeUpdatedBy accepts the
// permission object itself that is update. When the permission's key is not
// same-origin with this object's owner window, such as for secondary-keyed
// permissions like `3rdPartyFrameStorage^...`, MaybeUpdatedByNotifyOnly will
// be called with the updated window as an argument. MaybeUpdatedByNotifyOnly
// must be defined by PermissionStatus inheritors that are double-keyed.
virtual bool MaybeUpdatedBy(nsIPermission* aPermission) const;
virtual bool MaybeUpdatedByNotifyOnly(nsPIDOMWindowInner* aInnerWindow) const;
PermissionState ComputeStateFromAction(uint32_t aAction);
void PermissionChanged();
PermissionName mName;
RefPtr<PermissionStatusSink> mSink;
RefPtr<PermissionObserver> mObserver;
protected:
PermissionState mState;

View file

@ -1,231 +0,0 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "PermissionStatusSink.h"
#include "PermissionObserver.h"
#include "PermissionStatus.h"
#include "mozilla/Permission.h"
#include "mozilla/PermissionDelegateHandler.h"
#include "mozilla/PermissionManager.h"
#include "mozilla/dom/WorkerPrivate.h"
#include "mozilla/dom/WorkerRef.h"
namespace mozilla::dom {
PermissionStatusSink::PermissionStatusSink(PermissionStatus* aPermissionStatus,
PermissionName aPermissionName,
const nsACString& aPermissionType)
: mSerialEventTarget(NS_GetCurrentThread()),
mPermissionStatus(aPermissionStatus),
mMutex("PermissionStatusSink::mMutex"),
mPermissionName(aPermissionName),
mPermissionType(aPermissionType) {
MOZ_ASSERT(aPermissionStatus);
MOZ_ASSERT(mSerialEventTarget);
nsCOMPtr<nsIGlobalObject> global = aPermissionStatus->GetOwnerGlobal();
if (NS_WARN_IF(!global)) {
return;
}
nsCOMPtr<nsIPrincipal> principal = global->PrincipalOrNull();
if (NS_WARN_IF(!principal)) {
return;
}
mPrincipalForPermission = Permission::ClonePrincipalForPermission(principal);
}
PermissionStatusSink::~PermissionStatusSink() = default;
RefPtr<PermissionStatusSink::PermissionStatePromise>
PermissionStatusSink::Init() {
if (!NS_IsMainThread()) {
WorkerPrivate* workerPrivate = GetCurrentThreadWorkerPrivate();
MOZ_ASSERT(workerPrivate);
MutexAutoLock lock(mMutex);
mWorkerRef = WeakWorkerRef::Create(
workerPrivate, [self = RefPtr(this)] { self->Disentangle(); });
}
return InvokeAsync(GetMainThreadSerialEventTarget(), __func__,
[self = RefPtr(this)] {
MOZ_ASSERT(!self->mObserver);
// Covers the onchange part
// Whenever the user agent is aware that the state of a
// PermissionStatus instance status has changed: ... (The
// observer calls PermissionChanged() to do the steps)
self->mObserver = PermissionObserver::GetInstance();
if (NS_WARN_IF(!self->mObserver)) {
return PermissionStatePromise::CreateAndReject(
NS_ERROR_FAILURE, __func__);
}
self->mObserver->AddSink(self);
// Covers the query part (Step 8.2 - 8.4)
return self->ComputeStateOnMainThread();
});
}
bool PermissionStatusSink::MaybeUpdatedByOnMainThread(
nsIPermission* aPermission) {
MOZ_ASSERT(NS_IsMainThread());
if (!mPrincipalForPermission) {
return false;
}
nsCOMPtr<nsIPrincipal> permissionPrincipal;
aPermission->GetPrincipal(getter_AddRefs(permissionPrincipal));
if (!permissionPrincipal) {
return false;
}
return mPrincipalForPermission->Equals(permissionPrincipal);
}
bool PermissionStatusSink::MaybeUpdatedByNotifyOnlyOnMainThread(
nsPIDOMWindowInner* aInnerWindow) {
MOZ_ASSERT(NS_IsMainThread());
return false;
}
void PermissionStatusSink::PermissionChangedOnMainThread() {
MOZ_ASSERT(NS_IsMainThread());
ComputeStateOnMainThread()->Then(
mSerialEventTarget, __func__,
[self = RefPtr(this)](
const PermissionStatePromise::ResolveOrRejectValue& aResult) {
if (aResult.IsResolve() && self->mPermissionStatus) {
self->mPermissionStatus->PermissionChanged(aResult.ResolveValue());
}
});
}
void PermissionStatusSink::Disentangle() {
MOZ_ASSERT(mSerialEventTarget->IsOnCurrentThread());
mPermissionStatus = nullptr;
{
MutexAutoLock lock(mMutex);
mWorkerRef = nullptr;
}
NS_DispatchToMainThread(
NS_NewRunnableFunction(__func__, [self = RefPtr(this)] {
if (self->mObserver) {
self->mObserver->RemoveSink(self);
self->mObserver = nullptr;
}
}));
}
RefPtr<PermissionStatusSink::PermissionStatePromise>
PermissionStatusSink::ComputeStateOnMainThread() {
MOZ_ASSERT(NS_IsMainThread());
// Step 1: If settings wasn't passed, set it to the current settings object.
// Step 2: If settings is a non-secure context, return "denied".
// XXX(krosylight): No such steps here, and no WPT coverage?
// The permission handler covers the rest of the steps, although the model
// does not exactly match what the spec has. (Not passing "permission key" for
// example)
if (mSerialEventTarget->IsOnCurrentThread()) {
if (!mPermissionStatus) {
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE,
__func__);
}
RefPtr<nsGlobalWindowInner> window = mPermissionStatus->GetOwnerWindow();
return ComputeStateOnMainThreadInternal(window);
}
nsCOMPtr<nsPIDOMWindowInner> ancestorWindow;
nsCOMPtr<nsIPrincipal> workerPrincipal;
{
MutexAutoLock lock(mMutex);
if (!mWorkerRef) {
// We have been disentangled.
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE,
__func__);
}
// If we have mWorkerRef, we haven't received the WorkerRef notification
// yet.
WorkerPrivate* workerPrivate = mWorkerRef->GetUnsafePrivate();
MOZ_ASSERT(workerPrivate);
ancestorWindow = workerPrivate->GetAncestorWindow();
workerPrincipal = workerPrivate->GetPrincipal();
}
if (ancestorWindow) {
return ComputeStateOnMainThreadInternal(ancestorWindow);
}
if (NS_WARN_IF(!workerPrincipal)) {
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
RefPtr<nsIPermissionManager> permissionManager =
PermissionManager::GetInstance();
if (!permissionManager) {
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
uint32_t action = nsIPermissionManager::DENY_ACTION;
nsresult rv = permissionManager->TestPermissionFromPrincipal(
workerPrincipal, mPermissionType, &action);
if (NS_WARN_IF(NS_FAILED(rv))) {
return PermissionStatePromise::CreateAndReject(rv, __func__);
}
return PermissionStatePromise::CreateAndResolve(action, __func__);
}
RefPtr<PermissionStatusSink::PermissionStatePromise>
PermissionStatusSink::ComputeStateOnMainThreadInternal(
nsPIDOMWindowInner* aWindow) {
MOZ_ASSERT(NS_IsMainThread());
if (NS_WARN_IF(!aWindow)) {
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
RefPtr<Document> document = aWindow->GetExtantDoc();
if (NS_WARN_IF(!document)) {
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
uint32_t action = nsIPermissionManager::DENY_ACTION;
PermissionDelegateHandler* permissionHandler =
document->GetPermissionDelegateHandler();
if (NS_WARN_IF(!permissionHandler)) {
return PermissionStatePromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
}
nsresult rv = permissionHandler->GetPermissionForPermissionsAPI(
mPermissionType, &action);
if (NS_WARN_IF(NS_FAILED(rv))) {
return PermissionStatePromise::CreateAndReject(rv, __func__);
}
return PermissionStatePromise::CreateAndResolve(action, __func__);
}
} // namespace mozilla::dom

Some files were not shown because too many files have changed in this diff Show more