Vue开发实践:解决Chrome浏览器禁止通过代码关闭窗口的问题

前言

        在开发 Electron 桌面端应用时,软件有一个退出软件的按钮,用于关闭应用程序。然而,在实现这一功能的过程中,我们可能会遇到一些问题。本文将探讨这个问题,并给出解决方案。       

实现

        询问负责 Electron 的同学,得知直接关闭当前窗口就行。

        没有花多少时间去思考,第一时间赶到的代码是 window.close();

        但是实际运行一下发现并没有关闭窗口,打开控制栏发现警告 " 只能关闭由代码打开的窗口 ":

Vue开发实践:解决Chrome浏览器禁止通过代码关闭窗口的问题_第1张图片

        这是因为 Chrome 浏览器的安全限制,window.close() 方法只能在通过 window.open() 方法或脚本创建的窗口中调用。这意味着我们只能关闭由 JavaScript 打开的窗口或标签页。

        解决原理

        网上查询了下相关解决方法,发现解决方案都是: 通过 JavaScript 打开一个新窗口到自身,新窗口(具有"由 JavaScript 创建"属性)会覆盖原来的窗口(不具有 "由 JavaScript 创建"属性),然后再执行 window.close() 即可关闭窗口。

        以下是各种方法汇总:

序号 关闭代码 需要确认 无任何作用 无需确认 测试
1 window.close() IE7 firefox,chrome, safari Opera Close
2 window.opener=null; window.open('','_self'); window.close(); firefox IE7,Opera, chrome,safari Close
3 window.open('','_self'); window.close(); firefox IE7,Opera, chrome,safari Close
4 window.opener=null; window.close(); IE7 firefox,safari chrome,Opera Close
5 const opened=window.open('about:blank','_self'); opened.opener=null; opened.close(); firefox safari,IE7, chrome,Opera Close
6 const opened=window.open('about:blank','_self'); opened.close(); safari,firefox firefox,IE7, chrome,Opera Close

        但是经过我的测试,以上统统只能跳转到空白页,并没有实现关闭窗口!

        问题原因

        偶然的,我发现在首页(此时 history 栈只有当前页记录)点击关闭软件按钮可以完美的实现功能,一旦进入软件,再返回首页点击关闭软件按钮就只能跳转到空白页。那么问题就出在历史记录上面,查阅发现是因为 Chrome 浏览器为了保护用户数据的安全,不允许直接关闭包含历史记录的窗口。历史记录是用户在浏览器中浏览过的网页记录,如果允许直接关闭窗口,可能会导致用户丢失未保存的浏览数据,或者导致误操作关闭了包含重要信息的窗口。

       那么我们知道是因为存在历史记录导致我们的代码无法正确执行,那么让历史记录一直为空就好了,参考我之前写的 Element UI导航菜单之秘:无痕迹浏览与历史记录栈的管理 ,将项目内所有路由跳转从 push 修改为 replace 模式,这样 history 栈就会一直为当前页对应记录,就不会影响到我们关闭窗口了。

        解决方案

  1. 通过 JavaScript 打开一个新窗口到自身,新窗口(具有"由 JavaScript 创建"属性)会覆盖原来的窗口(不具有 "由 JavaScript 创建"属性),然后再执行 window.close() 即可关闭窗口。
  2. 将项目的路由跳转从 push 修改为 replace 模式。这样,history 栈就会一直为当前页对应记录,就不会影响到我们关闭网页了。

        需要注意的是,以上方法可能会影响到用户的使用体验,因为用户无法使用历史记录回退前进功能了。因此,在决定是否使用这些方法时,需要权衡利弊。


总结

        虽然最后我们实现代码关闭窗口的功能,但是我也在想:用户无法使用历史记录回退/前进功能了,虽然我们也可以再自己设置实体按键。但是用户真的需要这么一个实体关闭按钮吗?用户自身不能点击右上角关闭吗?

        在某些情况下,我们需要监听用户的关闭行为,但有时我们也无需这么做。那么在某些情况下这个关闭按钮的需求就是伪需求,属于不合理的需求,我们应该直接对产品说出 delete it!删除掉这个退出实体按钮是更好的选择!至于功能,用户自己会动手。


你可能感兴趣的:(前端,chrome,前端,前端框架,vue.js,javascript,electron)