我怎样才能强制来自浏览器-window 的外部链接在 Electron 的默认浏览器中打开?
How can I force external links from browser-window to open in a default browser from Electron?
我正在使用 BrowserWindow 显示应用程序,我想强制在默认浏览器中打开外部链接。这是可能的还是我必须以不同的方式处理这个问题?
我还没有对此进行测试,但我认为这应该有效:
1) 获取 BrowserWindow
的 WebContents
var wc = browserWindow.webContents;
2) 注册 WebContent
的 will-navigate
并拦截 navigation/link 次点击:
wc.on('will-navigate', function(e, url) {
/* If url isn't the actual page */
if(url != wc.getURL()) {
e.preventDefault();
openBrowser(url);
}
}
3) 使用 child_process
实现 openBrowser
。 Linux 桌面示例:
var openBrowser(url) {
require('child_process').exec('xdg-open ' + url);
}
让我知道这是否适合你!
我想出了这个,在检查了之前答案的解决方案之后。
mainWindow.webContents.on('new-window', function(e, url) {
e.preventDefault();
require('electron').shell.openExternal(url);
});
根据 electron spec,单击外部链接时会触发 new-window
。
注意:要求您在锚标签上使用 target="_blank"
。
如果您没有在 anchor
元素中使用 target="_blank"
,这可能对您有用:
const shell = require('electron').shell;
$(document).on('click', 'a[href^="http"]', function(event) {
event.preventDefault();
shell.openExternal(this.href);
});
任何路过的人。
我的用例:
我在我的应用程序中使用 SimpleMDE,它的预览模式在同一个 window 中打开链接。我希望所有链接都在默认 OS 浏览器中打开。我根据其他答案将此片段放在我的 main.js 文件中。它在创建新的 BrowserWindow 实例后调用它。我的实例称为 mainWindow
let wc = mainWindow.webContents
wc.on('will-navigate', function (e, url) {
if (url != wc.getURL()) {
e.preventDefault()
electron.shell.openExternal(url)
}
})
检查请求的 url 是否为外部 link。如果是,则使用 shell.openExternal
.
mainWindow.webContents.on('will-navigate', function(e, reqUrl) {
let getHost = url=>require('url').parse(url).host;
let reqHost = getHost(reqUrl);
let isExternal = reqHost && reqHost != getHost(wc.getURL());
if(isExternal) {
e.preventDefault();
electron.shell.openExternal(reqUrl);
}
}
将其放入 renderer side js
文件中。它将在用户的默认浏览器中打开 http
、https
链接。
没有JQuery附件!不需要 target="_blank"
!
let shell = require('electron').shell
document.addEventListener('click', function (event) {
if (event.target.tagName === 'A' && event.target.href.startsWith('http')) {
event.preventDefault()
shell.openExternal(event.target.href)
}
})
从已接受的答案中得到改进;
- link 必须是
target="_blank"
;
添加 background.js
(或您创建 window 的任何地方):
window.webContents.on('new-window', function(e, url) {
// make sure local urls stay in electron perimeter
if('file://' === url.substr(0, 'file://'.length)) {
return;
}
// and open every other protocols on the browser
e.preventDefault();
shell.openExternal(url);
});
注意: 为确保在所有应用程序 windows 中执行此行为,此代码应在每次 window 创建后 运行。
对于 Electron 5,这对我有用:
在 main.js
(你创建浏览器 window 的地方),在你的主要 require 语句中包含 'shell'(通常在文件的顶部),例如:
// Modules to control application life and create native browser window
const {
BrowserWindow,
shell
} = require('electron');
在 createWindow()
函数中,在 mainWindow = new BrowserWindow({ ... })
之后添加这些行:
mainWindow.webContents.on('new-window', function(e, url) {
e.preventDefault();
shell.openExternal(url);
});
我通过以下步骤解决了问题
- 在
const {app, BrowserWindow} = require('electron')
上添加 shell
const {app, BrowserWindow, shell} = require('electron')
- 设置 nativeWindowOpen 为 true
function createWindow () {
// Create the browser window.
const mainWindow = new BrowserWindow({
width: 1350,
height: 880,
webPreferences: {
nativeWindowOpen: true,
preload: path.join(__dirname, 'preload.js')
},
icon: path.join(__dirname, './img/icon.icns')
})
- 添加如下监听代码
mainWindow.webContents.on('will-navigate', function(e, reqUrl) {
let getHost = url=>require('url').parse(url).host;
let reqHost = getHost(reqUrl);
let isExternal = reqHost && reqHost !== getHost(wc.getURL());
if(isExternal) {
e.preventDefault();
shell.openExternal(reqUrl, {});
}
})
参考 by 崔西萍
我倾向于在外部 .js
脚本中使用这些行:
let ele = document.createElement("a");
let url = "https://google.com";
ele.setAttribute("href", url);
ele.setAttribute("onclick", "require('electron').shell.openExternal('" + url + "')");
new-window
现在已弃用,取而代之的是 Electron 12 中的 setWindowOpenHandler
(参见 https://github.com/electron/electron/pull/24517)。
所以更新的答案是:
mainWindow.webContents.setWindowOpenHandler(({ url }) => {
shell.openExternal(url);
return { action: 'deny' };
});
我正在使用 BrowserWindow 显示应用程序,我想强制在默认浏览器中打开外部链接。这是可能的还是我必须以不同的方式处理这个问题?
我还没有对此进行测试,但我认为这应该有效:
1) 获取 BrowserWindow
WebContents
var wc = browserWindow.webContents;
2) 注册 WebContent
的 will-navigate
并拦截 navigation/link 次点击:
wc.on('will-navigate', function(e, url) {
/* If url isn't the actual page */
if(url != wc.getURL()) {
e.preventDefault();
openBrowser(url);
}
}
3) 使用 child_process
实现 openBrowser
。 Linux 桌面示例:
var openBrowser(url) {
require('child_process').exec('xdg-open ' + url);
}
让我知道这是否适合你!
我想出了这个,在检查了之前答案的解决方案之后。
mainWindow.webContents.on('new-window', function(e, url) {
e.preventDefault();
require('electron').shell.openExternal(url);
});
根据 electron spec,单击外部链接时会触发 new-window
。
注意:要求您在锚标签上使用 target="_blank"
。
如果您没有在 anchor
元素中使用 target="_blank"
,这可能对您有用:
const shell = require('electron').shell;
$(document).on('click', 'a[href^="http"]', function(event) {
event.preventDefault();
shell.openExternal(this.href);
});
任何路过的人。
我的用例:
我在我的应用程序中使用 SimpleMDE,它的预览模式在同一个 window 中打开链接。我希望所有链接都在默认 OS 浏览器中打开。我根据其他答案将此片段放在我的 main.js 文件中。它在创建新的 BrowserWindow 实例后调用它。我的实例称为 mainWindow
let wc = mainWindow.webContents
wc.on('will-navigate', function (e, url) {
if (url != wc.getURL()) {
e.preventDefault()
electron.shell.openExternal(url)
}
})
检查请求的 url 是否为外部 link。如果是,则使用 shell.openExternal
.
mainWindow.webContents.on('will-navigate', function(e, reqUrl) {
let getHost = url=>require('url').parse(url).host;
let reqHost = getHost(reqUrl);
let isExternal = reqHost && reqHost != getHost(wc.getURL());
if(isExternal) {
e.preventDefault();
electron.shell.openExternal(reqUrl);
}
}
将其放入 renderer side js
文件中。它将在用户的默认浏览器中打开 http
、https
链接。
没有JQuery附件!不需要 target="_blank"
!
let shell = require('electron').shell
document.addEventListener('click', function (event) {
if (event.target.tagName === 'A' && event.target.href.startsWith('http')) {
event.preventDefault()
shell.openExternal(event.target.href)
}
})
从已接受的答案中得到改进;
- link 必须是
target="_blank"
; 添加
background.js
(或您创建 window 的任何地方):window.webContents.on('new-window', function(e, url) { // make sure local urls stay in electron perimeter if('file://' === url.substr(0, 'file://'.length)) { return; } // and open every other protocols on the browser e.preventDefault(); shell.openExternal(url); });
注意: 为确保在所有应用程序 windows 中执行此行为,此代码应在每次 window 创建后 运行。
对于 Electron 5,这对我有用:
在
main.js
(你创建浏览器 window 的地方),在你的主要 require 语句中包含 'shell'(通常在文件的顶部),例如:// Modules to control application life and create native browser window const { BrowserWindow, shell } = require('electron');
在
createWindow()
函数中,在mainWindow = new BrowserWindow({ ... })
之后添加这些行:mainWindow.webContents.on('new-window', function(e, url) { e.preventDefault(); shell.openExternal(url); });
我通过以下步骤解决了问题
- 在
const {app, BrowserWindow} = require('electron')
上添加 shell
const {app, BrowserWindow, shell} = require('electron')
- 设置 nativeWindowOpen 为 true
function createWindow () {
// Create the browser window.
const mainWindow = new BrowserWindow({
width: 1350,
height: 880,
webPreferences: {
nativeWindowOpen: true,
preload: path.join(__dirname, 'preload.js')
},
icon: path.join(__dirname, './img/icon.icns')
})
- 添加如下监听代码
mainWindow.webContents.on('will-navigate', function(e, reqUrl) {
let getHost = url=>require('url').parse(url).host;
let reqHost = getHost(reqUrl);
let isExternal = reqHost && reqHost !== getHost(wc.getURL());
if(isExternal) {
e.preventDefault();
shell.openExternal(reqUrl, {});
}
})
参考
我倾向于在外部 .js
脚本中使用这些行:
let ele = document.createElement("a");
let url = "https://google.com";
ele.setAttribute("href", url);
ele.setAttribute("onclick", "require('electron').shell.openExternal('" + url + "')");
new-window
现在已弃用,取而代之的是 Electron 12 中的 setWindowOpenHandler
(参见 https://github.com/electron/electron/pull/24517)。
所以更新的答案是:
mainWindow.webContents.setWindowOpenHandler(({ url }) => {
shell.openExternal(url);
return { action: 'deny' };
});