diff --git a/src/browser/base/content/ZenUIManager.mjs b/src/browser/base/content/ZenUIManager.mjs index 082d98206..009c70fb0 100644 --- a/src/browser/base/content/ZenUIManager.mjs +++ b/src/browser/base/content/ZenUIManager.mjs @@ -86,9 +86,7 @@ var gZenUIManager = { }, generateUuidv4() { - return '10000000-1000-4000-8000-100000000000'.replace(/[018]/g, (c) => - (+c ^ (crypto.getRandomValues(new Uint8Array(1))[0] & (15 >> (+c / 4)))).toString(16) - ); + return Services.uuid.generateUUID().toString(); }, toogleBookmarksSidebar() { diff --git a/src/browser/base/content/zen-glance.inc.xhtml b/src/browser/base/content/zen-glance.inc.xhtml index 61c7bf385..64d5a0703 100644 --- a/src/browser/base/content/zen-glance.inc.xhtml +++ b/src/browser/base/content/zen-glance.inc.xhtml @@ -1,4 +1,4 @@ - - + \ No newline at end of file + diff --git a/src/browser/base/content/zen-styles/zen-animations.css b/src/browser/base/content/zen-styles/zen-animations.css index 01c231662..067582958 100644 --- a/src/browser/base/content/zen-styles/zen-animations.css +++ b/src/browser/base/content/zen-styles/zen-animations.css @@ -227,76 +227,6 @@ } } -@keyframes zen-glance-content-animation-out { - 0% { - /* make the box shrink to final width/height and x/y coordinates */ - transform: translate(-50%, -50%) translateZ(0); - width: 85%; - height: 100%; - top: 50%; - left: 50%; - opacity: 1; - } - - 100% { - /* make the box appear from initial width/height and x/y coordinates */ - transform: translate(-50%, -50%) translateZ(0); - opacity: 0; - width: 47%; - height: 53%; - top: 50%; - left: 50%; - opacity: 0; - } -} - -@keyframes zen-glance-buttons-animation-full { - from { - width: 85%; - height: 85%; - top: 50%; - left: 50%; - transform: translate(-50%, -50%); - } - - to { - width: 100%; - height: 100%; - top: 50%; - left: 50%; - opacity: 1; - transform: translate(-50%, -50%); - } -} - -@keyframes zen-glance-loading-animation { - 0% { - opacity: 1; - width: 80%; - } - - 90% { - width: 100%; - } - - 100% { - opacity: 0; - } -} - -@keyframes zen-glance-buttons-animation { - from { - right: 0; - opacity: 0; - width: fit-content; - } - - to { - opacity: 1; - transform: translateX(-100%) translateY(-50%); - } -} - @keyframes zen-rice-form-out { 0% { transform: translateX(0); diff --git a/src/browser/base/content/zen-styles/zen-glance.css b/src/browser/base/content/zen-styles/zen-glance.css index 20b0f0e24..9256ef1f2 100644 --- a/src/browser/base/content/zen-styles/zen-glance.css +++ b/src/browser/base/content/zen-styles/zen-glance.css @@ -23,27 +23,38 @@ } } -.browserSidebarContainer.zen-glance-overlay { - box-shadow: none !important; +#zen-glance-sidebar-container { + position: absolute; + display: flex; + z-index: 999; - &[fade-out='true'] { - background: transparent; - opacity: 1; + &[hidden='true'] { + display: none; + } - & .browserContainer { - opacity: 1; - animation: zen-glance-content-animation-out 0.3s ease-in-out forwards !important; + top: 10%; + transform: translateY(-50%); - & browser { - opacity: 1 !important; - } + padding: 5px; + gap: 12px; + right: 1%; - & #zen-glance-sidebar-container { - opacity: 0; - transition: opacity 0.1s ease-in-out; - } + & toolbarbutton { + width: 32px; + height: 32px; + background: var(--zen-dialog-background); + border-radius: 999px; + appearance: none; + box-shadow: 0 0 12px 1px rgba(0, 0, 0, 0.07); + + & label { + display: none; } } +} + +.browserSidebarContainer.zen-glance-overlay { + box-shadow: none !important; & .browserContainer { background: var(--zen-dialog-background); @@ -69,37 +80,6 @@ overflow: hidden; } - & #zen-glance-sidebar-container { - position: absolute; - display: flex; - top: 10%; - left: 0; - transform: translateY(-50%); - opacity: 0; - background: var(--zen-dialog-background); - - border: 1px solid var(--zen-colors-border); - border-right: none; - - border-top-left-radius: var(--zen-native-inner-radius); - border-bottom-left-radius: var(--zen-native-inner-radius); - - padding: 5px; - gap: 6px; - - animation: zen-glance-buttons-animation 0.2s ease-in-out forwards; - animation-delay: 0.3s; - - & toolbarbutton { - width: 32px; - height: 32px; - - & label { - display: none; - } - } - } - & browser { width: 100%; height: 100%; @@ -116,22 +96,13 @@ &[animate='true'] { position: absolute; - transform: translate(-50%, -50%); + } + } - &:not([animate-end='true']) { - pointer-events: none; - - & browser { - opacity: 0; - visibility: hidden; - } - - & #zen-glance-sidebar-container { - opacity: 0; - animation: none; - pointer-events: none; - } - } + &[fade-out='true'] { + & browser { + transition: opacity 0.1s ease; + opacity: 0; } } } diff --git a/src/browser/base/content/zen-styles/zen-tabs/vertical-tabs.css b/src/browser/base/content/zen-styles/zen-tabs/vertical-tabs.css index 288b7d524..e17e45800 100644 --- a/src/browser/base/content/zen-styles/zen-tabs/vertical-tabs.css +++ b/src/browser/base/content/zen-styles/zen-tabs/vertical-tabs.css @@ -311,14 +311,23 @@ /* We have a tab inside a tab, this means, it's a glance tab */ & .tabbrowser-tab { pointer-events: none; - margin: 0; + margin: 0 0 0 4px; --toolbarbutton-inner-padding: 0; --border-radius-medium: 8px; + width: 24px; + height: 24px; + --tab-min-height: 24px; + --tab-min-width: 24px; & .tab-background { - background: transparent; + background: var(--zen-toolbar-element-bg) !important; + margin-block: 0 !important; + margin-inline: 0 !important; box-shadow: none !important; } + & .tab-content { + padding: 0 5px; + } & label { display: none !important; } & .tab-close-button, & .tab-reset-button { @@ -327,6 +336,8 @@ & .tab-icon-image { --toolbarbutton-inner-padding: 0 !important; + width: 14px; + height: 14px; } } diff --git a/src/browser/base/zen-components/ZenGlanceManager.mjs b/src/browser/base/zen-components/ZenGlanceManager.mjs index 38fc44495..ed2c93caa 100644 --- a/src/browser/base/zen-components/ZenGlanceManager.mjs +++ b/src/browser/base/zen-components/ZenGlanceManager.mjs @@ -1,11 +1,11 @@ { class ZenGlanceManager extends ZenDOMOperatedFeature { - #currentBrowser = null; - #currentTab = null; - _animating = false; _lazyPref = {}; + #glances = new Map(); + #currentGlanceID = null; + init() { window.addEventListener('keydown', this.onKeyDown.bind(this)); window.addEventListener('TabClose', this.onTabClose.bind(this)); @@ -24,17 +24,29 @@ Services.obs.addObserver(this, 'quit-application-requested'); } + get #currentBrowser() { + return this.#glances.get(this.#currentGlanceID)?.browser; + } + + get #currentTab() { + return this.#glances.get(this.#currentGlanceID)?.tab; + } + + get #currentParentTab() { + return this.#glances.get(this.#currentGlanceID)?.parentTab; + } + onKeyDown(event) { - if (event.key === 'Escape' && this.#currentBrowser) { + if (event.key === 'Escape' && this.#currentGlanceID) { event.preventDefault(); event.stopPropagation(); - this.closeGlance(); + this.closeGlance({ onTabClose: true }); } } onOverlayClick(event) { if (event.target === this.overlay && event.originalTarget !== this.contentWrapper) { - this.closeGlance(); + this.closeGlance({ onTabClose: true }); } } @@ -48,8 +60,8 @@ onUnload() { // clear everything - if (this.#currentBrowser) { - gBrowser.removeTab(this.#currentTab); + for (let [id, glance] of this.#glances) { + gBrowser.removeTab(glance.tab, { animate: false }); } } @@ -65,19 +77,49 @@ skipLoad: false, index: this.getTabPosition(currentTab), }; - this.currentParentTab = currentTab; + currentTab._selected = true; + const newUUID = gZenUIManager.generateUuidv4(); const newTab = existingTab ?? gBrowser.addTrustedTab(Services.io.newURI(url).spec, newTabOptions); if (currentTab.hasAttribute('zenDefaultUserContextId')) { newTab.setAttribute('zenDefaultUserContextId', true); } - gBrowser.selectedTab = newTab; currentTab.querySelector('.tab-content').appendChild(newTab); newTab.setAttribute('zen-glance-tab', true); - this.#currentBrowser = newTab.linkedBrowser; - this.#currentTab = newTab; + newTab.setAttribute('glance-id', newUUID); + currentTab.setAttribute('glance-id', newUUID); + this.#glances.set(newUUID, { + tab: newTab, + parentTab: currentTab, + browser: newTab.linkedBrowser, + }); + this.#currentGlanceID = newUUID; + setTimeout(() => { + gBrowser.tabContainer._invalidateCachedTabs(); // remove tiny tab from the tabstrip + }, 0); return this.#currentBrowser; } + fillOverlay(browser) { + this.overlay = browser.closest('.browserSidebarContainer'); + this.browserWrapper = browser.closest('.browserContainer'); + this.contentWrapper = browser.closest('.browserStack'); + } + + showSidebarButtons() { + if (this.sidebarButtons.hasAttribute('hidden')) { + gZenUIManager.motion.animate( + this.sidebarButtons.querySelectorAll('toolbarbutton'), + { x: [-50, 0], opacity: [0, 1] }, + { delay: gZenUIManager.motion.stagger(0.2) } + ); + } + this.sidebarButtons.removeAttribute('hidden'); + } + + hideSidebarButtons() { + this.sidebarButtons.setAttribute('hidden', true); + } + openGlance(data, existingTab = null, ownerTab = null) { if (this.#currentBrowser) { return; @@ -101,11 +143,8 @@ const browserElement = this.createBrowserElement(data.url, currentTab, existingTab); - this.overlay = browserElement.closest('.browserSidebarContainer'); - this.browserWrapper = browserElement.closest('.browserContainer'); - this.contentWrapper = browserElement.closest('.browserStack'); - - this.browserWrapper.prepend(this.sidebarButtons); + this.fillOverlay(browserElement); + this.showSidebarButtons(); this.overlay.classList.add('zen-glance-overlay'); @@ -115,11 +154,20 @@ this.overlay.removeAttribute('fade-out'); this.browserWrapper.setAttribute('animate', true); - this.browserWrapper.style.top = `${initialY + initialHeight / 2}px`; - this.browserWrapper.style.left = `${initialX + initialWidth / 2}px`; + const top = initialY + initialHeight / 2; + const left = initialX + initialWidth / 2; + this.browserWrapper.style.top = `${top}px`; + this.browserWrapper.style.left = `${left}px`; this.browserWrapper.style.width = `${initialWidth}px`; this.browserWrapper.style.height = `${initialHeight}px`; this.browserWrapper.style.opacity = 0.8; + this.#glances.get(this.#currentGlanceID).originalPosition = { + top: this.browserWrapper.style.top, + left: this.browserWrapper.style.left, + width: this.browserWrapper.style.width, + height: this.browserWrapper.style.height, + }; + this.browserWrapper.style.transform = 'translate(-50%, -50%)'; this.overlay.style.overflow = 'visible'; gZenUIManager.motion .animate( @@ -156,83 +204,88 @@ this.browserWrapper.removeAttribute('has-finished-animation'); if (noAnimation) { this.quickCloseGlance({ closeCurrentTab: false }); - this.#currentBrowser = null; - this.#currentTab = null; return; } this._animating = true; gBrowser._insertTabAtIndex(this.#currentTab, { - index: this.getTabPosition(this.currentParentTab), + index: this.getTabPosition(this.#currentParentTab), }); let quikcCloseZen = false; if (onTabClose) { // Create new tab if no more ex if (gBrowser.tabs.length === 1) { - gBrowser.selectedTab = gZenUIManager.openAndChangeToTab(Services.prefs.getStringPref('browser.startup.homepage')); + BrowserCommands.openTab(); return; - } else if (gBrowser.selectedTab === this.#currentTab) { - this._duringOpening = true; - gBrowser.tabContainer.advanceSelectedTab(1, true); // to skip the current tab - this._duringOpening = false; - quikcCloseZen = true; } } // do NOT touch here, I don't know what it does, but it works... - window.requestAnimationFrame(() => { - this.#currentTab.style.display = 'none'; - this.browserWrapper.removeAttribute('animate'); - this.browserWrapper.removeAttribute('animate-end'); - this.overlay.setAttribute('fade-out', true); - window.requestAnimationFrame(() => { - this.quickCloseGlance({ justAnimateParent: true }); - this.browserWrapper.setAttribute('animate', true); + this.#currentTab.style.display = 'none'; + this.overlay.setAttribute('fade-out', true); + this.overlay.style.pointerEvents = 'none'; + this.quickCloseGlance({ justAnimateParent: true, clearID: false }); + const originalPosition = this.#glances.get(this.#currentGlanceID).originalPosition; + gZenUIManager.motion + .animate( + this.browserWrapper, + { + ...originalPosition, + opacity: 0, + }, + { type: 'spring', bounce: 0, duration: 0.5 } + ) + .then(() => { + this.browserWrapper.removeAttribute('animate'); + this.browserWrapper.removeAttribute('animate-end'); + if (!this.#currentParentTab) { + return; + } + + if (!onTabClose || quikcCloseZen) { + this.quickCloseGlance({ clearID: false }); + } + this.overlay.removeAttribute('fade-out'); + this.browserWrapper.removeAttribute('animate'); + + this.lastCurrentTab = this.#currentTab; + + this.overlay.classList.remove('zen-glance-overlay'); + gBrowser._getSwitcher().setTabStateNoAction(this.lastCurrentTab, gBrowser.AsyncTabSwitcher.STATE_UNLOADED); + + if (!onTabClose) { + this.#currentParentTab._visuallySelected = false; + } + + // reset everything + const prevOverlay = this.overlay; + this.browserWrapper = null; + this.overlay = null; + this.contentWrapper = null; + + this.lastCurrentTab.removeAttribute('zen-glance-tab'); + this.lastCurrentTab._closingGlance = true; + + gBrowser.tabContainer._invalidateCachedTabs(); + gBrowser.removeTab(this.lastCurrentTab, { animate: false }); + this.#currentBrowser.remove(); + setTimeout(() => { - if (!this.currentParentTab) { - return; - } + prevOverlay.remove(); // Just to be sure + }, 0); - if (!onTabClose || quikcCloseZen) { - this.quickCloseGlance(); - } - this.overlay.removeAttribute('fade-out'); - this.browserWrapper.removeAttribute('animate'); + this.#currentParentTab.removeAttribute('glance-id'); - this.lastCurrentTab = this.#currentTab; + this.#glances.delete(this.#currentGlanceID); + this.#currentGlanceID = null; - this.overlay.classList.remove('zen-glance-overlay'); - gBrowser._getSwitcher().setTabStateNoAction(this.lastCurrentTab, gBrowser.AsyncTabSwitcher.STATE_UNLOADED); + this.lastCurrentTab = null; + this._duringOpening = false; - if (!onTabClose && gBrowser.selectedTab === this.lastCurrentTab) { - this._duringOpening = true; - gBrowser.selectedTab = this.currentParentTab; - } - - // reset everything - this.currentParentTab = null; - this.browserWrapper = null; - this.overlay = null; - this.contentWrapper = null; - - this.lastCurrentTab.removeAttribute('zen-glance-tab'); - this.lastCurrentTab._closingGlance = true; - - gBrowser.tabContainer._invalidateCachedTabs(); - gBrowser.removeTab(this.lastCurrentTab, { animate: true }); - - this.#currentTab = null; - this.#currentBrowser = null; - - this.lastCurrentTab = null; - this._duringOpening = false; - - this._animating = false; - }, 400); + this._animating = false; }); - }); } quickOpenGlance() { @@ -240,74 +293,106 @@ return; } this._duringOpening = true; - try { - gBrowser.selectedTab = this.#currentTab; - } catch (e) {} + this.showSidebarButtons(); - this.currentParentTab.linkedBrowser - .closest('.browserSidebarContainer') - .classList.add('deck-selected', 'zen-glance-background'); - this.currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('zen-glance-overlay'); - this.currentParentTab.linkedBrowser.zenModeActive = true; + const parentBrowserContainer = this.#currentParentTab.linkedBrowser.closest('.browserSidebarContainer'); + parentBrowserContainer.classList.add('deck-selected'); + parentBrowserContainer.classList.add('zen-glance-background'); + parentBrowserContainer.classList.remove('zen-glance-overlay'); + this.#currentParentTab.linkedBrowser.zenModeActive = true; + this.#currentParentTab.linkedBrowser.docShellIsActive = true; this.#currentBrowser.zenModeActive = true; - this.currentParentTab.linkedBrowser.docShellIsActive = true; this.#currentBrowser.docShellIsActive = true; this.#currentBrowser.setAttribute('zen-glance-selected', true); + this.fillOverlay(this.#currentBrowser); - this.currentParentTab._visuallySelected = true; + this.#currentParentTab._visuallySelected = true; this.overlay.classList.add('deck-selected'); + this.overlay.classList.add('zen-glance-overlay'); this._duringOpening = false; } - quickCloseGlance({ closeCurrentTab = true, closeParentTab = true, justAnimateParent = false } = {}) { - const parentHasBrowser = !!this.currentParentTab.linkedBrowser; + quickCloseGlance({ closeCurrentTab = true, closeParentTab = true, justAnimateParent = false, clearID = true } = {}) { + const parentHasBrowser = !!this.#currentParentTab.linkedBrowser; + this.hideSidebarButtons(); if (!justAnimateParent) { if (parentHasBrowser) { if (closeParentTab) { - this.currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('deck-selected'); + this.#currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('deck-selected'); } - this.currentParentTab.linkedBrowser.zenModeActive = false; + this.#currentParentTab.linkedBrowser.zenModeActive = false; } this.#currentBrowser.zenModeActive = false; if (closeParentTab && parentHasBrowser) { - this.currentParentTab.linkedBrowser.docShellIsActive = false; + this.#currentParentTab.linkedBrowser.docShellIsActive = false; } if (closeCurrentTab) { this.#currentBrowser.docShellIsActive = false; this.overlay.classList.remove('deck-selected'); + this.#currentTab._selected = false; } - if (!this.currentParentTab._visuallySelected && closeParentTab) { - this.currentParentTab._visuallySelected = false; + if (!this.#currentParentTab._visuallySelected && closeParentTab) { + this.#currentParentTab._visuallySelected = false; } this.#currentBrowser.removeAttribute('zen-glance-selected'); + this.overlay.classList.remove('zen-glance-overlay'); } if (parentHasBrowser) { - this.currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('zen-glance-background'); + this.#currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('zen-glance-background'); + } + if (clearID) { + this.#currentGlanceID = null; } } - onLocationChange(_) { - if (this._duringOpening) { + onLocationChange(browser) { + const tab = gBrowser.getTabForBrowser(browser); + if (this.animatingFullOpen) { return; } - if (gBrowser.selectedTab === this.#currentTab && !this.animatingOpen && !this._duringOpening && this.#currentBrowser) { - this.quickOpenGlance(); + if (this._duringOpening || !tab.hasAttribute('glance-id')) { + if (this.#currentGlanceID && !this._duringOpening) { + this.quickCloseGlance(); + } return; } - if (gBrowser.selectedTab === this.currentParentTab && this.#currentBrowser) { - this.quickOpenGlance(); - } else if ((!this.animatingFullOpen || this.animatingOpen) && this.#currentBrowser) { - this.closeGlance(); + if (this.#currentGlanceID && this.#currentGlanceID !== tab.getAttribute('glance-id')) { + this.quickCloseGlance(); + } + this.#currentGlanceID = tab.getAttribute('glance-id'); + if (gBrowser.selectedTab === this.#currentParentTab && this.#currentBrowser) { + setTimeout(this.quickOpenGlance.bind(this), 0); } } onTabClose(event) { - if (event.target === this.currentParentTab) { + if (event.target === this.#currentParentTab) { this.closeGlance({ onTabClose: true }); } } + manageTabClose(tab) { + if (tab.hasAttribute('glance-id')) { + const oldGlanceID = this.#currentGlanceID; + const newGlanceID = tab.getAttribute('glance-id'); + this.#currentGlanceID = newGlanceID; + const isDifferent = newGlanceID !== oldGlanceID; + if (this._ignoreClose) { + this._ignoreClose = false; + return false; + } + this._ignoreClose = true; + this.closeGlance({ noAnimation: isDifferent, onTabClose: true }); + if (isDifferent) { + this.#currentGlanceID = oldGlanceID; + } + // only keep continueing tab close if we are not on the currently selected tab + return !isDifferent; + } + return false; + } + tabDomainsDiffer(tab1, url2) { try { if (!tab1) { @@ -351,19 +436,22 @@ } fullyOpenGlance() { + this.animatingFullOpen = true; gBrowser._insertTabAtIndex(this.#currentTab, { index: this.getTabPosition(this.#currentTab), }); - this.animatingFullOpen = true; - this.currentParentTab._visuallySelected = false; + this.#currentParentTab._visuallySelected = false; this.browserWrapper.removeAttribute('style'); this.browserWrapper.removeAttribute('has-finished-animation'); this.browserWrapper.setAttribute('animate-full', true); this.#currentTab.removeAttribute('zen-glance-tab'); + this.#currentTab.removeAttribute('glance-id'); + this.#currentParentTab.removeAttribute('glance-id'); gBrowser.selectedTab = this.#currentTab; - this.currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('zen-glance-background'); + this.#currentParentTab.linkedBrowser.closest('.browserSidebarContainer').classList.remove('zen-glance-background'); + this.hideSidebarButtons(); gZenUIManager.motion .animate( this.browserWrapper, @@ -382,6 +470,7 @@ this.browserWrapper.removeAttribute('style'); this.animatingFullOpen = false; this.closeGlance({ noAnimation: true }); + this.#glances.delete(this.#currentGlanceID); }); } diff --git a/src/browser/base/zen-components/actors/ZenGlanceChild.sys.mjs b/src/browser/base/zen-components/actors/ZenGlanceChild.sys.mjs index 6a328f870..c43451375 100644 --- a/src/browser/base/zen-components/actors/ZenGlanceChild.sys.mjs +++ b/src/browser/base/zen-components/actors/ZenGlanceChild.sys.mjs @@ -96,7 +96,7 @@ export class ZenGlanceChild extends JSWindowActorChild { } handleClick(event) { - if (this.ensureOnlyKeyModifiers(event)) { + if (this.ensureOnlyKeyModifiers(event) || event.button !== 0 || event.defaultPrevented) { return; } const activationMethod = this._activationMethod; diff --git a/src/browser/components/tabbrowser/content/tabbrowser-js.patch b/src/browser/components/tabbrowser/content/tabbrowser-js.patch index 2234dfb64..2b45af37c 100644 --- a/src/browser/components/tabbrowser/content/tabbrowser-js.patch +++ b/src/browser/components/tabbrowser/content/tabbrowser-js.patch @@ -1,5 +1,5 @@ diff --git a/browser/components/tabbrowser/content/tabbrowser.js b/browser/components/tabbrowser/content/tabbrowser.js -index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb749b23d289 100644 +index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..9aaa4b0cd8a8bb76c59415f2322d739cbe00302e 100644 --- a/browser/components/tabbrowser/content/tabbrowser.js +++ b/browser/components/tabbrowser/content/tabbrowser.js @@ -406,11 +406,39 @@ @@ -219,19 +219,26 @@ index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb74 // Handle requests for synchronously removing an already // asynchronously closing tab. if (!animate && aTab.closing) { -@@ -4471,7 +4559,10 @@ +@@ -4457,7 +4545,9 @@ + // frame created for it (for example, by updating the visually selected + // state). + let tabWidth = window.windowUtils.getBoundsWithoutFlushing(aTab).width; +- ++ if (gZenGlanceManager.manageTabClose(aTab)) { ++ return; ++ } + if ( + !this._beginRemoveTab(aTab, { + closeWindowFastpath: true, +@@ -4471,7 +4561,6 @@ TelemetryStopwatch.cancel("FX_TAB_CLOSE_TIME_NO_ANIM_MS", aTab); return; } - -+ if (aTab.hasAttribute("zen-glance-tab")) { -+ gZenGlanceManager.closeGlance(); -+ return; -+ } let lockTabSizing = !this.tabContainer.verticalMode && !aTab.pinned && -@@ -4610,14 +4701,14 @@ +@@ -4610,14 +4699,14 @@ !!this.tabsInCollapsedTabGroups.length; if ( aTab.visible && @@ -248,7 +255,7 @@ index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb74 if (closeWindow) { // We've already called beforeunload on all the relevant tabs if we get here, -@@ -5465,10 +5556,10 @@ +@@ -5465,10 +5554,10 @@ SessionStore.deleteCustomTabValue(aTab, "hiddenBy"); } @@ -261,7 +268,7 @@ index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb74 aTab.selected || aTab.closing || // Tabs that are sharing the screen, microphone or camera cannot be hidden. -@@ -7443,6 +7534,7 @@ +@@ -7443,6 +7532,7 @@ aWebProgress.isTopLevel ) { this.mTab.setAttribute("busy", "true"); @@ -269,7 +276,7 @@ index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb74 gBrowser._tabAttrModified(this.mTab, ["busy"]); this.mTab._notselectedsinceload = !this.mTab.selected; gBrowser.syncThrobberAnimations(this.mTab); -@@ -8411,7 +8503,7 @@ var TabContextMenu = { +@@ -8411,7 +8501,7 @@ var TabContextMenu = { ); contextUnpinSelectedTabs.hidden = !this.contextTab.pinned || !multiselectionContext; @@ -278,7 +285,7 @@ index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb74 // Move Tab items let contextMoveTabOptions = document.getElementById( "context_moveTabOptions" -@@ -8444,7 +8536,7 @@ var TabContextMenu = { +@@ -8444,7 +8534,7 @@ var TabContextMenu = { let contextMoveTabToStart = document.getElementById("context_moveToStart"); let isFirstTab = tabsToMove[0] == visibleTabs[0] || @@ -287,7 +294,7 @@ index ff90a70bdad6c94ec4b90027ff102972d0eb28e5..6362493d8ec06aa90cc3425498c0fb74 contextMoveTabToStart.disabled = isFirstTab && allSelectedTabsAdjacent; document.getElementById("context_openTabInWindow").disabled = -@@ -8677,6 +8769,7 @@ var TabContextMenu = { +@@ -8677,6 +8767,7 @@ var TabContextMenu = { if (this.contextTab.multiselected) { gBrowser.removeMultiSelectedTabs(); } else { diff --git a/src/browser/components/tabbrowser/content/tabs-js.patch b/src/browser/components/tabbrowser/content/tabs-js.patch index 77a31a206..b6181fead 100644 --- a/src/browser/components/tabbrowser/content/tabs-js.patch +++ b/src/browser/components/tabbrowser/content/tabs-js.patch @@ -1,5 +1,5 @@ diff --git a/browser/components/tabbrowser/content/tabs.js b/browser/components/tabbrowser/content/tabs.js -index 8aeb244ffca9f48661805f5b7d860b5896055562..a6fae3e317afc9b681f818506c7f34a325e43df4 100644 +index 8aeb244ffca9f48661805f5b7d860b5896055562..a36fc2cb5761323fd40d367fd04234c45dd02404 100644 --- a/browser/components/tabbrowser/content/tabs.js +++ b/browser/components/tabbrowser/content/tabs.js @@ -94,7 +94,7 @@ @@ -104,7 +104,7 @@ index 8aeb244ffca9f48661805f5b7d860b5896055562..a6fae3e317afc9b681f818506c7f34a3 this.#allTabs = [ - ...this.verticalPinnedTabsContainer.children, -+ ...document.getElementById("zen-essentials-container").children, ...this.verticalPinnedTabsContainer.children, ++ ...document.getElementById("zen-essentials-container").children, ...this.verticalPinnedTabsContainer.children, ...children, ]; return this.#allTabs;