一、前言
前一章我们主要学习了如何使用模板来创建一个窗口,并顺带讲解了一下这个模板中的代码结构。
但总的来说,前面三个章节都只是在做准备工作而已。
而从本章开始,我们就正式踏入学习Electron的旅程了。
既然这个框架是做GUI软件的,那窗口自然就是最重要的,所以我们本章就以窗口开始学习。
二、了解窗口
首先我们需要明白的一个点就是:窗口不是应用程序!
正如前面章节从代码中看到的那样,app
这个实例代表当前这个应用程序。
但只有它还不够,因为没有窗口的命令行程序(也称CLI``,Command Line Interface
,命令行接口)也是程序,只不过两者的交互方式不一样而已。
窗口只是应用程序的一种交互方式,也就是我们常常能看到的GUI
(Graphical User Interface
,图形用户接口)。
所以一个应用程序既可以没有窗口,也可以创建多个窗口,只不过我们看到一个窗口的应用程序居多,因为其开发起来更加简单、使用起来更加简洁,仅此而已,
窗口就像一块画布,你是可以任意绘制的,不同框架提供的绘制方式并不相同。
对于Electron
框架来说,窗口就是通过html
、js
、css
这三大前端基石来完成的,所以学习本系列的前提是,你得学会这三个基础。
这三个并不难,一天你可能就能看完(可以跟着B站上的相关免费课程学习),自己试着写个小网页,一周估计就能练熟。
一个传统化的标准窗口程序一般会包含以下五个部分:
- 标题栏:即窗口最上面、包含最大最小化的那一行,还可以用于鼠标拖动窗口。
- 菜单栏:存放各种功能命令,一般在标题栏下方
- 工具栏:存放各种常用功能,一般在菜单栏下方,但在现代应用程序中已经很少见到了(
word
这种软件中你也还是能看到)。 - 内容区域:窗口正中间,工具栏的下方,这个区域就是我们可以发挥想象力的地方了,你可以在其中存放任何东西。
- 状态栏:窗口最下面,也就是内容区域的下面,用于显示一些状态信息的。
比如windows系统自带的记事本程序:
比如wps
的工具栏:
但这也仅仅只是传统的窗口模式,现在的很多应用程序已经逐渐开始模糊了各个区域的边界。
比如像上面看到的记事本、wps,它们的标题栏除了最基本的功能外,还多了一个标签页的功能,更加节约空间的同时也会更加美观。
但想要做到这一点并不容易,因为这超出了传统的窗口模式,系统本身的窗口是不支持的。
所以这就需要我们进行定制!
什么是定制呢?
前面我们提到了,按照传统模式来说,其实也就只有中间的内容区域可以任由我们自由发挥,其它区域都是有自己特定格式的,你并不能随意改动。
而定制的方法就是:禁用其它四个区域,只保留中间的内容区域。
然后重点就来了,由于内容区域我们是可以任意绘制的,所以我们就可以通过在内容区域自己绘制标题栏、菜单栏等等,从而实现整个应用程序高度自定义化!
三、了解BrowserWindow
有了前面的基础,我们就可以正式来聊聊Electron中的窗口了,Electron框架是通过BrowserWindow
类来创建一个窗口的,所以我们主要就是来看看这个类到底是怎么用的!
官方文档为:BrowserWindow。
学会看官方文档是个好习惯,因为我现在讲的东西可能一年后就过时了,但官方文档会一直保持在最新的状态。
虽然中文翻译过来看起来可能有点奇怪,但基本还是能看懂它的意思。
其官方文档的前部分作用基本就是我上图所标注的那样。
‘所属进程模块’这部分暂时不用过多理会,
Electron
中主要分主进程、渲染进程两种,但这个类实际上无论是主进程还是渲染进程都是可以使用的,后面我们再提。
从这里我们就能看到更多的内容,比如,这个窗口类不仅仅可以用loadFile
加载本地的html
文件作为窗口样式,也可以用函数loadURL
这个函数加载网页作为窗口。
还有前面用的在app.on('ready', createWindow);
这里也提到了,就是要等这个事件之后才能创建窗口。
事件一般有两种使用方式,一种就是最开始用的,直接将事件封装成为了一个函数:app.whenReady()
。
但更常用的还是用通用函数on
,然后第一个参数传入你想要等待的事件即可,而第二个参数就是你想要在这个事件发生后要执行的函数。
由于这个类是Electron
中的核心类,里面的东西非常之多。我也不可能一个一个挨着说完,所以这里只给大家稍微理一理即可。
从右边的目录看起,class BrowserWindow
前面的内容都是官方将其最常见的用法写出来,教我们怎么用。这个后面我也会聊聊。
然后class BrowserWindow
后面的内容才是真正在开始介绍这个类中有哪些东西。
不过由于它的内容太多了!所以我这里也只能分类聊聊他们的区别,然后后面再挑几个常用的讲一讲。
首先是这个带new
的,这是在实例化一个对象。
实例化对象很多时候都需要很多选项,比如前面我们填的窗口宽高,你都可以在这里找到,除此之外你还能看到相当多的其它属性,可以自己试一试。
然后下面的就是事件:
用法如上图,最简单的就是举个例子:
//省略创建窗口win实例的过程
win.on('page-title-updated',(event,title,explicitSet)=>{
})
第二、三个你可能知道,一个是字符串(string),一个是布尔(boolean),那么第一个事件(Event)是什么鬼呢?
不知道没关系,你可以在代码中直接用函数console.log
函数将它打印一下就行了,这就是一个对象而已。
其它事件的使用方法也是同理,后面如果用到了会再提。
然后是静态方法:
静态方法比前面的实例方法用起来要简单一点,因为你不用创建窗口就可以直接使用这些方法,就像上面官方文档所示的那样:
let wins=BrowserWindow.getAllWindows(); //获取当前所有窗口,返回值是一个窗口数组
官方文档这方面已经介绍的很详细了,我就不再多说了。
唯一你可能觉得疑惑的就是,这些返回值都是什么意思?
其实不用管它,凡是这种不知道什么东西的类型,一般都是自定义对象,你只要用console.log
函数打印一下它就知道它里面都有写什么东西了。
接下来是实例属性:
只要带有实例二字的,就是需要你先创建好一个窗口才能使用的东西,只能通过创建好的这个实例进行调用。
实例属性就是我们创建的这个窗口上有哪些东西,比如这里的webContents
,又是一个对象,具体这个对象有哪些东西,可以点官方所示文档进去查看。
还有这里的id
,就是用来标识当前窗口的一个数字,后面跟了只读两个字,就意味着你不能更改它,但你能读取它:
console.log(win.id); //打印窗口的id
最后就是实例方法:
当你创建了窗口之后,你就可以通过这些函数来控制这个窗口的行为,比如这里的destroy()
方法,就可以用来强制关闭这个窗口。