參考并擴展自
Creating a markdown app with Electron and React
簡介
Electron是一個使用js來開發(fā)跨平臺桌面端軟件的一個框架。
比較著名的產(chǎn)品包括:
- VS code
- skype
- atom
- 釘釘
- SwitchHosts!
重點
- electron的原理是把chromium的v8引擎和node的運行時結(jié)合到了一起。
- 架構(gòu)還是前后端分離
- 前端按照web開發(fā)的方式正常開發(fā)
- 通信原理:每一個前端窗口是一個進程,后端單獨是一個進程半等。electron提供前后端進程間通信的接口带欢。
開發(fā)流程
前提條件
有一個可以跑通的web項目念颈,比如用create-react-app創(chuàng)建的項目汗销。
安裝electron
npm install electron --save-dev
在package.json的script中添加
"electron-start": "electron ."
在package.json的頂層添加
"main": "public/main.js"
此時的package.json看起來是這樣的
{
"name": "mook",
"version": "0.1.0",
"main": "public/main.js",
"private": true,
"dependencies": {
"react": "^15.6.1",
"react-dom": "^15.6.1",
"react-scripts": "1.0.13"
},
"scripts": {
"start": "react-scripts start",
"build": "react-scripts build",
"test": "react-scripts test --env=jsdom",
"eject": "react-scripts eject",
"electron-start": "electron ."
},
"devDependencies": {
"electron": "^1.7.6"
}
}
main.js文件是后端主進程的執(zhí)行入口,內(nèi)容如下:
const electron = require('electron');
const app = electron.app;
const BrowserWindow = electron.BrowserWindow;
let mainWindow;
function createWindow() {
mainWindow = new BrowserWindow({width: 900, height: 680});
mainWindow.loadURL('http://localhost:3000');
app.setAboutPanelOptions({
applicationName: "Mook",
applicationVersion: "0.0.1",
})
mainWindow.on('closed', () => mainWindow = null);
}
app.on('ready', createWindow);
app.on('window-all-closed', () => {
if (process.platform !== 'darwin') {
app.quit();
}
});
app.on('activate', () => {
if (mainWindow === null) {
createWindow();
}
});
其中mainWindow.loadURL('http://localhost:3000');
這行為加載的前端頁面的地址抬吟。
此時,先執(zhí)行npm run start
啟動前端頁面统抬,再執(zhí)行npm run electron-start
啟動electron火本。
簡化開發(fā)啟動
每次啟動都需要執(zhí)行兩個命令,比較麻煩聪建,因此钙畔,可以通過安裝幾個包來解決這個問題。
npm install wait-on concurrently --save-dev
然后再package.json文件的script中添加
"electron-dev": "concurrently \"npm start\" \"wait-on http://localhost:8080 && electron .\"",
這樣金麸,就可以通過執(zhí)行npm run electron-dev
一個命令啟動了擎析。
創(chuàng)建打包腳本
- 首先需要安裝打包工具
npm install electron-builder --save-dev
- 添加打包配置
然后再package.json文件的script中添加
"preelectron-pack": "npm run build"
以及
"electron-pack": "build -c.extraMetadata.main=build/main.js"
preelectron-pack
命令會在執(zhí)行npm run electron-pack
之前自動執(zhí)行,也就是會先打包前端的代碼挥下,生成一個html文件揍魂。
需要注意的是桨醋,build/main.js就是剛剛package.json文件中的public/main.js。只不過在打包前端代碼的時候一并打包入了build目錄中现斋。如果你用的不是create-react-app喜最,那么需要注意把這個文件一起打包進去。
在package.json中庄蹋,需要增加一個build塊和homepage屬性瞬内,build用來告訴electron-pack如何打包,而homepage則指明了js和css文件的位置限书。配置如下:
"homepage": "./",
"build": {
"appId": "com.mook",
"files": [
"build/**/*",
"node_modules/**/*"
],
"directories": {
"buildResources": "assets"
}
}
- 修改main.js
之前的main.js是加載了http://localhost:3000
的方式進行的虫蝶。打包后不能繼續(xù)使用這種方法。需要安裝一個包
npm install electron-is-dev --save
這個包用來判斷當前執(zhí)行的環(huán)境蔗包。
之后修改public/main.js
const isDev = require('electron-is-dev');
const path = require('path');
將原來的
mainWindow.loadURL('http://localhost:3000');
改為
mainWindow.loadURL(isDev ? 'http://localhost:3000' : `file://${path.join(__dirname, '../build/index.html')}`);
- 打包
執(zhí)行npm run electron-pack
就會生成dmg文件秉扑。
至此整個項目的架子基本就已經(jīng)搭完了。
前后端通信
electron提供了ipcMain和ipcRenderer兩個類進行通信调限。
前端發(fā)送請求
const {ipcRenderer} = window.require('electron')
ipcRenderer.send(channel, data)
其中 channel
可以理解為調(diào)用的方法名舟陆,需要后端對該方法進行監(jiān)聽。
后端接受請求
const { ipcMain } = electron
ipcMain.on(channel, (event, arg) => {
# do something here
})
反過來
后端發(fā)送請求
mainWindow.webContents.send(channel, data)
其中mainWindow為項目啟動時創(chuàng)建的窗口耻矮,如果創(chuàng)建了多個窗口秦躯,可以向指定的窗口發(fā)送請求。
前端監(jiān)聽請求
const {ipcRenderer} = window.require('electron')
ipcRenderer.on(channel, (event, arg) => {
# do something here
})
小結(jié)
以上是開發(fā)工程中遇到的比較費時間的一些事情的整理裆装。electron用來開發(fā)一些小工具還是一個不錯的選擇踱承。