You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何检测浏览器扩展以Popup还是Side Panel模式运行?

检测浏览器扩展的加载模式(Popup/Chrome侧面板/Firefox侧边栏)

我正在开发一款可同时以Popup、基于Chrome内核浏览器的Side Panel或Firefox的Sidebar模式打开的浏览器扩展,想知道能否通过JavaScript检测当前用户使用的是哪种加载模式?

我的manifest.json片段如下:

{
  "manifest_version": 3,
  "permissions": [
    "storage",
    "unlimitedStorage",
    "activeTab",
    "tabs",
    "sidePanel",
    "declarativeNetRequestWithHostAccess"
  ],
  "action": {
    "default_popup": "index.html"
  },
  "background": {
    "service_worker": "js/background.js"
  },
  "side_panel": {
    "default_path": "index.html"
  },
  "sidebar_action": {
    "default_panel": "index.html",
    "default_icon": "icons/icon_128.png"
  }
}

另外我发现扩展在Popup和侧边栏模式下,browser对象中都存在sidePanel,未发现两者差异。


可行的检测方法

1. 结合窗口尺寸与浏览器API区分

Popup有默认尺寸限制(Chrome默认最大宽800、高600),而侧面板/侧边栏的高度接近浏览器窗口高度,宽度固定在侧边栏范围。可以通过尺寸特征结合专属API判断:

function detectLoadMode() {
  // 侧面板/侧边栏的宽高比明显为竖长型
  const isVerticalPanel = window.innerWidth < 500 && window.innerHeight > window.innerWidth * 2;
  
  if (isVerticalPanel) {
    // Firefox侧边栏有专属sidebarAction API
    if (typeof browser?.sidebarAction !== 'undefined') {
      return 'firefox-sidebar';
    }
    // Chrome侧面板有专属sidePanel API
    else if (typeof chrome?.sidePanel !== 'undefined') {
      return 'chrome-side-panel';
    }
  } 
  // Popup尺寸更均衡,且不会超过默认限制(若用户未手动修改)
  else if (window.innerHeight <= 600 && window.innerWidth <= 800) {
    return 'popup';
  }
  
  return 'unknown';
}

2. 通过当前页面URL匹配manifest配置

读取扩展清单中的入口路径,对比当前页面的URL后缀,直接判断加载来源:

function detectLoadMode() {
  const manifest = chrome.runtime.getManifest();
  const currentPath = window.location.pathname;

  if (currentPath.endsWith(manifest.action.default_popup)) {
    return 'popup';
  } else if (currentPath.endsWith(manifest.side_panel.default_path)) {
    return 'chrome-side-panel';
  } else if (currentPath.endsWith(manifest.sidebar_action.default_panel)) {
    return 'firefox-sidebar';
  }
  
  return 'unknown';
}

3. 利用tabs API的上下文差异

在Popup中调用chrome.tabs.getCurrent()会返回undefined,而侧面板/侧边栏环境下能获取到当前活动标签页信息,以此区分Popup和面板模式:

async function detectLoadMode() {
  try {
    const tab = await chrome.tabs.getCurrent();
    // Popup中无法获取当前tab
    if (!tab) {
      return 'popup';
    } else {
      // 再区分Chrome和Firefox面板
      if (typeof browser?.sidebarAction !== 'undefined') {
        return 'firefox-sidebar';
      } else if (typeof chrome?.sidePanel !== 'undefined') {
        return 'chrome-side-panel';
      }
    }
  } catch (err) {
    return 'unknown';
  }
}

注意点

  • 跨浏览器兼容时,优先判断专属API而非仅依赖chrome/browser命名空间,避免API覆盖导致误判。
  • 窗口尺寸判断可能因用户手动调整Popup尺寸失效,建议结合多种方法提升检测准确性。

内容的提问来源于stack exchange,提问作者Bartosz Perończyk

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.20 10:53:17