当前位置: 首页 > Web前端 > HTML

【Electron】酷家乐客户端开发实践分享——入坑

时间:2023-04-02 21:12:41 HTML

作者:酷家乐PC客户端负责人钟力原文地址:https://webfe.kujiale.com/electron-ku-jia-le-ke-hu-duan-kai-fa-shi-jian-fen-xiang-ru-keng-zhi-nan/酷家乐客户端:下载地址https://www.kujiale.com/activity/136文章背景:我们积累了很多酷家乐客户端V12改版成功后的宝贵经验和最佳实践。前端社区对Electron的了解比较少,所以希望以系列文章的形式分享这方面的内容。系列文章:【Electron】酷家乐客户端开发实践分享-入坑【Electron】酷家乐客户端开发实践分享-软件自动更新【Electron】酷家乐客户端开发实践分享-浏览器启动客户端【Electron】酷家乐客户端开发实践分享-进程通信【Electron】酷家乐客户端开发实践分享-下载管理器不定时更新...本文初衷是Electron(JavaScript、NodeJs、HTML、CSS)和web前端工程师使用的技术栈完美契合。因此,越来越多的前端工程师使用Electron进行桌面客户端开发,我就是其中之一。Electron技术栈虽然对前端工程师比较友好,但是它的概念很多,和web前端开发有很大区别。希望能写一篇入坑指南,帮助读者快速上手Electron。了解客户端首先提出一个问题,Web应用程序是桌面客户端吗?很明显不是。那么,问题来了,桌面客户端到底是一款什么样的软件呢?既然要从Web前端转为客户端开发,就需要像了解Web应用一样了解客户端。回到刚才的问题,桌面客户端有两个重要的特点:独立于操作系统运行(桌面客户端只是一台PC,所以仅限于windows、macOS、linux等主流PC操作系统)并拥有自己的GUI(用户图形用户界面)Web应用程序具有自己的GUI,并且必须在浏览器中执行,因此它们不是桌面客户端。浏览器可以直接在操作系统上运行,并且有自己的图形用户界面,所以浏览器是一个桌面客户端。Electron的能力当我第一次接触Electron时,我被它的文档弄得眼花缭乱。加班的深夜,忍不住向天长感叹:这东西能干什么?这东西能做什么?在经历了Electron的反复磨擦之后,总结了Electron的几个关键能力:NodeJs的所有能力、与操作系统的交互、操作系统、操作系统相关的操作、HTTP(s)、HTTP2process、子进程、进程相关filesystem,filesystem...省略了Electron提供的基础模块,主要与操作系统app主进程生命周期管理交互,控制macOStaskbardock,windowstaskbartaskbarBrowserWindow控制窗口,windows在macOS和windows中都很重要!screen操作用户显示globalShortcut系统级快捷键...省略Chromium提供的能力,主要提供GUI图形界面解析HTML、CSS、JSajax请求cookie、localstorage...省略的能力越大,责任越大如果用户安装了我们的Desktopclient,那么当我们的软件运行在用户的电脑上时,我们就拥有了很大的权利,这是一把双刃剑。用户选择了我们的软件,我们也对用户的电脑负责。能力越大,责任越大:1.注意内存占用,尤其是chromium,简直就是内存怪兽。通过OS获取用户计算机的配置,然后根据计算机的配置和可用资源制定合理的策略。为软件添加代码签名以提高安全性。小心操作注册表和用户敏感目录。一旦被贴上【流氓软件】或【不好用】的标签,就很难改变用户的印象。主进程、渲染进程生命周期主进程:这个进程从整个应用程序的开始到结束都存在。只有一个主要过程。渲染进程:主进程可以创建/销毁渲染进程,因此渲染进程的生命周期是不固定的。可以有多个渲染进程。执行环境在Electron的API文档中,模块可用的进程会在文档的顶部标识,例如:ipcRenderer划分主进程的职责,渲染进程控制app的生命周期,注册keyapp的事件,解析HTML,阻止一些默认渲染窗口内容的行为,比如webContents的跳转,下载事件的默认行为等(在渲染过程中不能做)处理的交互逻辑创建BrowserWindow的窗口,也就是渲染过程。合理设置窗口的参数,控制窗口的生命周期(比如什么时候销毁窗口),确定BrowserWindow在何处加载HTML并与主进程通信,实现高级交互窗口和前端资源我们来回顾一下刚才提到的执行过程,包括一个有趣的点是Electron的窗口会加载一个HTML来渲染窗口的内容。HTML,以及HTML加载的css、js文件统称为前端资源。如果不加载HTML,客户端还能使用吗?让我们试试吧//主进程constwin1=newBrowserWindow();constwin2=newBrowserWindow();上面的代码在主进程中执行,创建了两个窗口,窗口中没有加载HTML文件。但是这个窗口是真实存在的,有系统标配的控制条,可以拖动,是正宗的系统窗口!我们可以发现前端资源和窗口是分离的。主进程创建的窗口(BrowserWindow)既是系统原生窗口,也是加载渲染前端资源的容器窗口。通常,前端资源是通过file协议和http(s)协议来加载的。接下来,我们就来看看这两种方式的区别。通过文件协议加载HTML在Electron官方介绍的例子中,通过文件协议加载HTML就是通过文件协议加载HTML。不管有没有网络,都可以加载HTML文件。这是文件协议的核心优势。缺点也很明显:如果页面资源需要更新,只能通过发布版本来解决(如果使用webview,可以自动更新webview的内容,但是webview也需要有网络才能加载)。文件协议下,无法通过Ajax请求数据(不同协议),只能通过NodeJs的http(s)模块发起网络请求。通过http协议加载HTML。通过http协议加载HTML。好处是可以通过网页的部署随时更新渲染进程的资源。而在https协议下,可以在前端使用我们熟悉的ajax请求来获取页面上的数据。当然缺点也很明显:没有网络,当你不缓存HTML时,你窗口的内容无法加载,必须通过https加载才能保证页面内容的安全。代码示例方便读者更好的理解以上内容。我写了一个小demo,源码地址是https://github.com/littlecold233/electron-demo,例子有以下特点:创建主窗口,防止关闭主窗口的默认事件,不摧毁窗户。(大部分客户端的主窗口,在关闭主窗口的时候,实际上是隐藏了窗口,比如QQ,微信)当应用程序退出时,会尝试关闭所有窗口,然后再退出应用程序。如果阻塞了主窗口关闭行为的默认事件,则主窗口无法关闭,整个应用程序无法退出。所以用变量forceQuit来控制。使用http或者file协议加载window前端资源(例子中默认加载微信)const{app,BrowserWindow}=require('electron')asyncfunctionmain(){awaitapp.whenReady();让forceQuit=false;constmajorWindow=newBrowserWindow({title:'主窗口',width:1000,height:750,minWidth:1000,minHeight:750,backgroundColor:'#f2f2f2',});//主窗口//防止标题更新majorWindow.on('page-title-updated',(e)=>{e.preventDefault();});majorWindow.on('close',(e)=>{//当用户要注销时,不处理,如果(forceQuit)return;e.preventDefault();//macOS默认销毁窗口全屏处理hide();//隐藏窗口}});//点击dock打开主窗口app.on('activate',()=>{majorWindow.show();});//用户使用cmd+Q,在代码中调用app.quit等//这时候用户希望能够退出应用,所以将forceQuit改为trueapp.on('before-quit',()=>{forceQuit=true;});app.dock.setIcon('./img/icon.png');//App打包后,这行代码其实是不需要的majorWindow.loadURL('https://wx.qq.com');//HTTP协议加载前端资源,随便加载一个微信试试//majorWindow.loadURL('file://index.html');//文件协议加载前端资源}main();本地运行本例最后欢迎大家在评论区讨论,技术交流&内推->zhongli@qunhemail.com