menus.create()

使用定義了選單項屬性的物件來建立一個選單項。

與其他非同步函式不同,這個函式不返回 Promise,而是使用一個可選的回撥函式來通訊成功或失敗。這是因為它的返回值是新項的 ID。

為了與其他瀏覽器相容,Firefox 在 contextMenus 名稱空間和 menus 名稱空間中都提供了此方法。但是,使用 contextMenus 名稱空間無法建立工具選單項 (contexts: ["tools_menu"])。

在持久化和非持久化擴充套件中建立選單

你建立選單項的方式取決於你的擴充套件是否使用

  • 非持久化後臺頁面(事件頁面),在這種情況下,選單會在瀏覽器和擴充套件重啟後仍然存在。你需要從 runtime.onInstalled 監聽器中呼叫 menus.create(帶有一個選單特定的 ID)。這可以避免在頁面重啟時重複嘗試建立選單項,這在頂層呼叫時會發生。
  • 持久化後臺頁面
    • 在 Chrome 中,持久化後臺頁面的選單項是持久化的。在 runtime.onInstalled 監聽器中建立你的選單。
    • 在 Firefox 中,持久化後臺頁面的選單項永遠不會持久化。在頂層無條件呼叫 menus.create 來註冊選單項。

有關更多資訊,請參閱背景指令碼頁面上的 初始化擴充套件 和 Extension Workshop 上的 事件驅動的背景指令碼

語法

js
browser.menus.create(
  createProperties, // object
  () => {/* … */}   // optional function
)

引數

createProperties

object。新選單項的屬性。

checked 可選

boolean。複選框或單選按鈕項的初始狀態:true 表示選中,false 表示未選中。在給定的一組單選按鈕項中,一次只能選中一個單選按鈕項。

command 可選

string。描述使用者點選該項時應執行的操作的字串。可識別的值包括:

  • "_execute_browser_action":模擬點選擴充套件的瀏覽器操作,如果它有彈出視窗則開啟(僅限 Manifest V2)
  • "_execute_action":模擬點選擴充套件的操作,如果它有彈出視窗則開啟(僅限 Manifest V3)
  • "_execute_page_action":模擬點選擴充套件的頁面操作,如果它有彈出視窗則開啟
  • "_execute_sidebar_action":開啟擴充套件的側邊欄

有關詳細資訊,請參閱 manifest.json 鍵 commands 中特殊快捷方式的文件。

當指定了可識別值之一時,點選該項不會觸發 menus.onClicked 事件;相反,會觸發預設操作,例如開啟彈出視窗。否則,點選該項將觸發 menus.onClicked,並且可以使用該事件來實現回退行為。

contexts 可選

array of menus.ContextType。將顯示此選單項的上下文陣列。如果省略此選項

  • 如果項的父項設定了上下文,則此項將繼承其父項的上下文
  • 否則,該項將被賦予一個上下文陣列 ["page"]。
documentUrlPatterns 可選

array of string。允許你將該項限制為僅應用於 URL 與給定 匹配模式 之一匹配的文件。這同樣適用於框架。

enabled 可選

boolean。此選單項是啟用還是停用。預設為 true

icons 可選

object。一個或多個要顯示在該項旁邊的自定義圖示。自定義圖示只能為出現在子選單中的項設定。此屬性是一個物件,其中包含每個提供的圖示的一個屬性:屬性的名稱應包含圖示的畫素大小,路徑是相對於擴充套件根目錄的圖示路徑。瀏覽器會嘗試選擇一個 16x16 畫素的圖示用於正常顯示,或一個 32x32 畫素的圖示用於高密度顯示。為避免任何縮放,你可以這樣指定圖示:

js
browser.menus.create({
  icons: {
    16: "path/to/geo-16.png",
    32: "path/to/geo-32.png",
  },
});

或者,你也可以指定一個單一的 SVG 圖示,它會被適當地縮放

js
browser.menus.create({
  icons: {
    16: "path/to/geo.svg",
  },
});

注意: 頂層選單項使用 manifest 中指定的 圖示,而不是此鍵中指定的圖示。

id 可選

string。要分配給此項的唯一 ID。對於 Manifest V2 中的非持久化 後臺(事件)頁面 和 Manifest V3 是必需的。不能與此擴充套件的其他 ID 相同。

onclick 可選

function。點選選單項時呼叫的函式。事件頁面不能使用此函式:相反,它們應該為 menus.onClicked 註冊一個監聽器。

parentId 可選

integerstring。父選單項的 ID;這使該項成為先前新增的項的子項。注意:如果你建立了多個選單項,那麼這些項將被放置在一個子選單中。子選單的父項將以擴充套件的名稱進行標記。

targetUrlPatterns 可選

array of string。與 documentUrlPatterns 類似,但允許你根據 anchor 標籤的 href 以及 img/audio/video 標籤的 src 屬性進行過濾。此引數支援任何 URL 方案,即使是通常不允許在匹配模式中使用的方案。

title 可選

string。將在項中顯示的文字。除非 type 為 "separator",否則為必需。

你可以在字串中使用 %s。如果你在選單項中使用此項,並且當選單顯示時頁面上選中了一些文字,那麼選中的文字將被插入到標題中。例如,如果 title 是 "Translate '%s' to Pig Latin",使用者選擇了單詞 "cool",然後激活了選單,那麼選單項的標題將是:"Translate 'cool' to Pig Latin"。

如果標題包含一個 ampersand "&",則下一個字元將被用作該項的訪問鍵,ampersand 將不會顯示。例外情況是

  • 如果下一個字元也是一個 ampersand:那麼將顯示一個 ampersand,並且不會設定訪問鍵。實際上,"&&" 用於顯示單個 ampersand。
  • 如果下一個字元是插值指令 "%s":那麼 ampersand 將不會顯示,也不會設定訪問鍵。
  • 如果 ampersand 是標題中的最後一個字元:那麼 ampersand 將不會顯示,也不會設定訪問鍵。

只有一個 ampersand 會被用來設定訪問鍵:後續的 ampersands 將不會顯示,但也不會設定鍵。所以 "&A and &B" 將顯示為 "A and B" 並將 "A" 設定為訪問鍵。

在某些 Firefox 的本地化版本(日語和中文)中,訪問鍵會用括號括起來並附加到選單標籤上,除非選單標題本身已經以訪問鍵結尾(例如 "toolkit(&K)")。有關更多詳細資訊,請參閱 Firefox bug 1647373

type 可選

menus.ItemType。選單項的型別:"normal", "checkbox", "radio", "separator"。預設為 "normal"。

viewTypes 可選

extension.ViewType。將顯示選單項的檢視型別列表。預設為任何檢視,包括那些沒有 viewType 的檢視。

visible 可選

boolean。該項是否在選單中顯示。預設為 true

callback 可選

function。在項建立後呼叫。如果建立項時有任何問題,詳細資訊將在 runtime.lastError 中提供。

返回值

integerstring。新建立項的 ID

示例

此示例建立一個上下文選單項,該選單項在使用者在頁面上選擇了某些文字時顯示。它只是將選定的文字記錄到控制檯

js
browser.menus.create({
  id: "log-selection",
  title: "Log '%s' to the console",
  contexts: ["selection"],
});

browser.menus.onClicked.addListener((info, tab) => {
  if (info.menuItemId === "log-selection") {
    console.log(info.selectionText);
  }
});

此示例添加了兩個單選按鈕項,您可以使用它們來選擇是將綠色還是藍色邊框應用於頁面。請注意,此示例需要 activeTab 許可權

js
function onCreated() {
  if (browser.runtime.lastError) {
    console.log("error creating item:", browser.runtime.lastError);
  } else {
    console.log("item created successfully");
  }
}

browser.menus.create(
  {
    id: "radio-green",
    type: "radio",
    title: "Make it green",
    contexts: ["all"],
    checked: false,
  },
  onCreated,
);

browser.menus.create(
  {
    id: "radio-blue",
    type: "radio",
    title: "Make it blue",
    contexts: ["all"],
    checked: false,
  },
  onCreated,
);

let makeItBlue = 'document.body.style.border = "5px solid blue"';
let makeItGreen = 'document.body.style.border = "5px solid green"';

browser.menus.onClicked.addListener((info, tab) => {
  if (info.menuItemId === "radio-blue") {
    browser.tabs.executeScript(tab.id, {
      code: makeItBlue,
    });
  } else if (info.menuItemId === "radio-green") {
    browser.tabs.executeScript(tab.id, {
      code: makeItGreen,
    });
  }
});

擴充套件程式示例

瀏覽器相容性

注意: 此 API 基於 Chromium 的 chrome.contextMenus API。本文件源自 Chromium 程式碼中的 context_menus.json