From 3ac8f803c9210f37c329ede7d7aa24b9245ab43e Mon Sep 17 00:00:00 2001 From: Abe Jellinek Date: Thu, 18 Jan 2024 17:29:40 -0500 Subject: [PATCH] Fix duplicate creator context menus, extract utility function --- chrome/content/zotero/elements/itemBox.js | 21 ++++++++++---- chrome/content/zotero/itemPane.js | 6 +--- .../zotero/xpcom/utilities_internal.js | 28 +++++++++++++++++++ 3 files changed, 45 insertions(+), 10 deletions(-) diff --git a/chrome/content/zotero/elements/itemBox.js b/chrome/content/zotero/elements/itemBox.js index af970fa306..b07234f7b9 100644 --- a/chrome/content/zotero/elements/itemBox.js +++ b/chrome/content/zotero/elements/itemBox.js @@ -626,7 +626,10 @@ rowData.oncontextmenu = (event) => { this._linkMenu.dataset.link = link; document.popupNode = rowLabel.parentElement; - this.handlePopupOpening(event, this._id('zotero-link-menu')); + + let menupopup = this._id('zotero-link-menu'); + Zotero.Utilities.Internal.updateEditContextMenu(menupopup, !event.target.closest('input')); + this.handlePopupOpening(event, menupopup); }; } @@ -1062,9 +1065,14 @@ optionsButton.setAttribute('data-l10n-id', "itembox-button-options"); let triggerPopup = (e) => { document.popupNode = firstlast; + + let menupopup = this._id('zotero-creator-transform-menu'); + let hideEditMenuItems = !e.target.closest('input'); + Zotero.Utilities.Internal.updateEditContextMenu(menupopup, hideEditMenuItems); + this._id('creator-transform-swap-names').hidden = fieldMode > 0; this._id('creator-transform-capitalize').disabled = !this.canCapitalizeCreatorName(rowData.parentNode); - this.handlePopupOpening(e, this._id('zotero-creator-transform-menu')); + this.handlePopupOpening(e, menupopup); }; rowData.appendChild(optionsButton); @@ -2118,6 +2126,10 @@ * @return {Promise} */ async swapNames(_event) { + if (this.saveOnEdit) { + await this.blurOpenField(); + } + var row = document.popupNode.closest('.meta-row'); var typeBox = row.querySelector('[fieldname]'); var creatorIndex = parseInt(typeBox.getAttribute('fieldname').split('-')[1]); @@ -2127,10 +2139,8 @@ fields.lastName = firstName; fields.firstName = lastName; this.modifyCreator(creatorIndex, fields); + if (this.saveOnEdit) { - // If a field is open, blur it, which will trigger a save and cause - // the saveTx() to be a no-op - await this.blurOpenField(); await this.item.saveTx(); } } @@ -2382,6 +2392,7 @@ } handlePopupOpening(event, popup) { + event.stopPropagation(); let isRightClick = event.type == 'contextmenu'; if (!isRightClick) { event.target.style.visibility = "visible"; diff --git a/chrome/content/zotero/itemPane.js b/chrome/content/zotero/itemPane.js index e5ce72f9b8..932307b598 100644 --- a/chrome/content/zotero/itemPane.js +++ b/chrome/content/zotero/itemPane.js @@ -282,12 +282,8 @@ var ZoteroItemPane = new function() { let valueSentenceCased = Zotero.Utilities.sentenceCase(value); let menupopup = document.createXULElement('menupopup'); - if (includeEditMenuOptions) { - // eslint-disable-next-line no-undef - goBuildEditContextMenu(); - let menuitems = [...document.getElementById('textbox-contextmenu').children]; - menupopup.append(...menuitems.map(menuitem => menuitem.cloneNode(true))); + Zotero.Utilities.Internal.updateEditContextMenu(menupopup); menupopup.append(document.createXULElement('menuseparator')); } diff --git a/chrome/content/zotero/xpcom/utilities_internal.js b/chrome/content/zotero/xpcom/utilities_internal.js index 9d520e9ec8..0999852f0d 100644 --- a/chrome/content/zotero/xpcom/utilities_internal.js +++ b/chrome/content/zotero/xpcom/utilities_internal.js @@ -2327,6 +2327,34 @@ Zotero.Utilities.Internal = { document.documentElement.removeChild(scrollDiv); return scrollbarWidth; + }, + + updateEditContextMenu(menupopup, hideEditMenuItems = false) { + for (let menuitem of Array.from(menupopup.children)) { + if (!menuitem.hasAttribute('data-edit-menu-item')) { + break; + } + menuitem.remove(); + } + + let win = menupopup.ownerDocument.defaultView; + let editPopup = win.goBuildEditContextMenu(); + let editMenuItems = Array.from(editPopup.children).map((menuitem) => { + menuitem = menuitem.cloneNode(true); + menuitem.setAttribute('data-edit-menu-item', 'true'); + if (hideEditMenuItems) { + menuitem.hidden = true; + } + return menuitem; + }); + if (!hideEditMenuItems && menupopup.childElementCount) { + let separator = win.document.createXULElement('menuseparator'); + separator.setAttribute('data-edit-menu-item', 'true'); + editMenuItems.push(separator); + } + menupopup.prepend(...editMenuItems); + + win.goUpdateGlobalEditMenuItems(true); } };