Toc
  1. 新建项目
Toc
0 results found
Kristy Zhang
从无到有开发electron+react+typescript桌面客户端(一)

新建项目

  1. 新建
mkdir desk-annual-lottery   
cd desk-annual-lottery
npm init
npm install electron --save-dev //汗 公司的网络这一步就失败了,咋也装不上

eletron安装失败的解决方案
新建.npmrc文件,添加一行配置

electron_mirror=https://npm.taobao.org/mirrors/electron/

重新执行electron的安装命令

亲测有效

继续

mkdir web //用于放置前端相关代码
mkdir app //electron的

//用自己想要的脚手架创建一个web 模板应用,这里我用的umi
cd web
npx @umijs/create-umi-app //报错的话就先安装一下 npm i @umijs/create-umi-app -g
npm install
cd app

编写app代码,创建main.ts

import {app, BrowserWindow} from 'electron';
import path from 'path';
let mainWindow: Electron.BrowserWindow;
/**
*
*/
function createWindow(): void {
// Create the browser window.
mainWindow = new BrowserWindow({
height: 600,
webPreferences: {
preload: path.join(__dirname, 'preload.js'),
},
width: 800,
});
// and load the index.html of the app.
mainWindow.loadFile(path.join(__dirname, '../html/index.html'));
// Open the DevTools.
mainWindow.webContents.openDevTools();
// Emitted when the window is closed.
mainWindow.on('closed', () => {
// Dereference the window object, usually you would store windows
// in an array if your app supports multi windows, this is the time
// when you should delete the corresponding element.
mainWindow = null as any;
});
}
// This method will be called when Electron has finished
// initialization and is ready to create browser windows.
// Some APIs can only be used after this event occurs.
app.on('ready', createWindow);
// Quit when all windows are closed.
app.on('window-all-closed', () => {
// On OS X it is common for applications and their menu bar
// to stay active until the user quits explicitly with Cmd + Q
if (process.platform !== 'darwin') {
app.quit();
}
});
app.on('activate', () => {
// On OS X it"s common to re-create a window in the app when the
// dock icon is clicked and there are no other windows open.
if (mainWindow === null) {
createWindow();
}
});
// In this file you can include the rest of your app"s specific main process
// code. You can also put them in separate files and require them here.

创建preload.ts

// All of the Node.js APIs are available in the preload process.
// It has the same sandbox as a Chrome extension.
window.addEventListener("DOMContentLoaded", () => {
const replaceText = (selector: string, text: string) => {
const element = document.getElementById(selector);
if (element) {
element.innerText = text;
}
};
for (const type of ["chrome", "node", "electron"]) {
replaceText(`${type}-version`, (process.versions as any)[type]);
}
});

返回根目录,创建tsconfig.json

{
"compilerOptions": {
"target": "esnext",
"module": "commonjs",
"moduleResolution": "node",
"resolveJsonModule": true,
"importHelpers": true,
"esModuleInterop": true,
"sourceMap": true,
"baseUrl": "./",
"strict": true,
"paths": {
"*": ["node_modules/*"]
},
"allowSyntheticDefaultImports": true,
"outDir": "./dist",
},
"include": [
"app/**/*"
],
}

package.json添加script命令

"scripts": {
"build": "tsc",
"watch": "tsc -w",
"start": "npm run build && electron ./dist/main.js"
},

根目录创建html文件夹(先测试以下运行),进入文件夹创建index.html页面

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>年会抽奖</title>
</head>
<body>
测试
</body>
</html>

运行
npm start//如果运行失败,提示缺少什么库,npm 装一下,再重新运行

程序启动如图
electron-demo-01.jpg

  1. 将开发环境中引入的html页面替换成web中的页面,相对来说还是比较简单的

    // mainWindow.loadFile(path.join(__dirname, '../html/index.html'));
    mainWindow.loadURL('http://localhost:8000/');
  2. 调试
    网页端的调试就不多说了,主要讲一下electron的debug
    官网上有案例,直接复制过来
    .vscode目录下新建launch.json

{
"version": "0.2.0",
"configurations": [
{
"name": "Debug Main Process",
"type": "node",
"request": "launch",
"cwd": "${workspaceFolder}",
"runtimeExecutable": "${workspaceFolder}/node_modules/.bin/electron",
"windows": {
"runtimeExecutable": "${workspaceFolder}/node_modules/.bin/electron.cmd"
},
"args": ["."]
}
]
}

在代码里需要debug的地方输入debugger
F5开始调试代码

  1. 区分当前环境
    package.json
"scripts": {
"dev": "set NODE_ENV=development && tsc && electron ./build/main.js",
"build": "set NODE_ENV=production && tsc",
"pro": "npm run build && electron ./build/main.js"
},

main.ts

...

const node_env = process.env.NODE_ENV;

...

if (node_env === 'development') {
mainWindow.loadURL('http://localhost:8000/');
} else {
//web中.umirc.ts中设置 outputPath: '../dist',
mainWindow.loadFile(path.join(__dirname, '../dist/index.html'));
}

...

这里生产环境会有几个问题

  • 本地资源不做额外开发不支持browser模式,故将.umirc中的history type改为hash路由.
  • web打包以后的路径会引用不到资源,是因为静态资源路径错误,publicPath改为相对路径
history: {
type: 'hash',
},
publicPath: './',

到此为止,一个简单的开发版本已经完成,下一篇会介绍打包成客户端的步骤

打赏
支付宝
微信
本文作者:Kristy Zhang
版权声明:本文首发于Kristy Zhang的博客,转载请注明出处!