Example project address: github.com/klren0312/e…

View related accumulated knowledge: github.com/klren0312/d…

I. Electron introduction

Electron is an open source project maintained by GitHub and an active community of contributors. Build cross-platform desktop applications using JavaScript, HTML, and CSS

Characteristics of 1.

  • Cross-platform can be packaged as Mac, Windows, and Linux applications

  • Simplified desktop development (1) Electron is based on Chromium and Node.js and can build applications using HTML, CSS and JavaScript (2) Electron API and NodeJS API

  • The community is active

2. The compatibility

Xp is out of the question and NWJS and other solutions may be needed

Ii. Project construction

1. Use the Vue CLI to create a VUE project

vue create electron-test
Copy the code

2. Install the plug-in vue-cli-plugin-electron- Builder

vue add electron-builder
Copy the code

3. Some changes in the project after the plug-in is installed

① Package. json added several scripts

NPM Run electron: Serve electron Development mode NPM Run electron: Build electron packingCopy the code

Postinstall and postuninstall are intended to ensure that they always match electron when installing or removing dependencies

Background-js file added

The main process-related operations are written in this file

③ An environment variable is added

It can be used to determine if it’s in the electron state

process.env.IS_ELECTRON
Copy the code

Iii. Development summary

1. Configure the project icon

IO /vue-cli-plu… nklayman.github.

Using the electric-icon-Builder, generate an icon that conforms to electron

(1) the installation

npm install --save-dev electron-icon-builder
Copy the code

② Configure the generate command in package.json

"electron:generate-icons": "electron-icon-builder --input=./public/icon.png --output=build --flatten"
Copy the code

Step 3 Generate ICONS

npm run electron:generate-icons
Copy the code

(4) using

import path from 'path'
const win = new BrowserWindow({
  icon: path.join(__static, 'icon.png')})Copy the code

2. Failed to Fetch Extension is displayed when the project development mode is running

Warning: Vue devtool cannot be downloaded in development mode due to network problems. Comment out the downloaded code in background.js

3. The project uses local Vue DevTools

① You can clone the vue devTools code and compile it

git clone https://github.com/vuejs/vue-devtools.git
cd vue-devtools
npm install
npm run build
Copy the code

Then copy the vue-devtools/ Packages/shell-Chrome folder to the project root directory

Js file in app.on(‘ready’) life cycle

// Use the local vUE developer tools
session.defaultSession.loadExtension(path.resolve('shell-chrome'))
Copy the code

(3) When creating a window, use the following example method to display the vUE developer tools normally

// src/background.js
if (process.env.WEBPACK_DEV_SERVER_URL) {
  await transferWin.loadURL(
    process.env.WEBPACK_DEV_SERVER_URL + '/#/test'
  )
  if(! process.env.IS_TEST) transferWin.webContents.openDevTools() }else {
  transferWin.loadURL('app://./index.html' + '/#/test')}Copy the code

4. How to use NodeJS API in rendering process

NodeIntegration needs to be set to true in vue.config.js

module.exports = {
  pluginOptions: {
    electronBuilder: {
      nodeIntegration: true}}}Copy the code

Or when you create a window

win = new BrowserWindow({
    width: 500.height: 400.frame: false.transparent: true.backgroundColor: '# 00000000'.// When closing developer tools, a new render view is created, so the configured background color is used, and the default white is used if not
    webPreferences: {
      nodeIntegration: true.// Render layer can use Node
      webSecurity: false./ / across domains
      enableRemoteModule: true // Remote can be used
    },
    // eslint-disable-next-line no-undef
    icon: path.resolve(__static, 'logo.png')})Copy the code

5. Create Windows that cross domains

When creating a window, configure webSecurity: false

6. How to monitor the state of the window, minimize, focus, hide the window, show the window, close the window

// Window minimization triggers
win.on('minimize'.() = > {
  console.log(Minimize)
})
win.on('focus'.() = > {
  console.log('focus')})// Window hidden, taskbar no icon
win.on('hide'.() = > {
  console.log('hide')
})
win.on('show'.() = > {
  flashTray(false)
  console.log('show')})Copy the code

7. How to create a tray icon

Reference: www.electronjs.org/docs/api/tr…

let tray = null
function createTray ({
  tray = newTray (path) resolve (__static, 'logo. The PNG'))// Set the tray icon
  const contextMenu = Menu.buildFromTemplate([
     new MenuItem({
      label'Exit program'.click() = > {
        isQuit = true
        app.exit()
      }
    })
  ])
  tray.setContextMenu(contextMenu) // Set the right-click menuTray. On (" click ",() = > { // The tray click event
    if (win.isVisible()) {
      win.focus()
    } else {
      win.show()
    }
  })
}
Copy the code

Listen for the main window to close, if not exit completely, then just hide the window

win.on('close'.e= > {
    if (isQuit) {
      win = null
    } else {
      e.preventDefault()
      win.hide()
    }
})
Copy the code

8. Tray flashing and taskbar flashing

① The principle of tray flashing is to switch the tray icon regularly, and the switch between the icon and the transparent icon

let flashInterval
function flashTray (bool{
  if(! bool) { flashInterval &&clearInterval(flashInterval)
    tray.setImage(path.resolve(__static, 'logo.png'))
    return
  }
  flashInterval && clearInterval(flashInterval)
  var count = 0
  flashInterval = setInterval(function({
    if (count++ % 2= =0) {
      tray.setImage(path.resolve(__static, 'empty.png'))}else {
      tray.setImage(path.resolve(__static, 'logo.png'}})),400)}Copy the code

② The flicker of the taskbar

win.flashFrame(true) / / highlight
Copy the code

9. How do I only run a single instance

Reference: www.electronjs.org/docs/api/ap…

If your program is a major instances of application and when app. RequestSingleInstanceLock () returns true, you should continue to make your program is running. If it returns false, exit immediately

const gotTheLock = app.requestSingleInstanceLock()
if(! gotTheLock) { app.quit() } { app.on('second-instance'.(event, argv) = > {
    if (process.platform === 'win32') {
      if (win) {
        if (win.isMinimized()) {
          win.restore()
        }
        if (win.isVisible()) {
          win.focus()
        } else {
          win.show()
        }
      }     }
  })
}
Copy the code

10. How does the main process communicate with the renderer process

Reference Documents:

ipcMain ipcRenderer

① Rendering process

Const {ipcRenderer} = require('electron') ipcrenderer. send('message', 'ping') // Send to ipcrenderer. on('message-reply', (event, arg) => { console.log(arg) // pong }Copy the code

(2) the main process

// Listen for renderer information
ipcMain.on('message'.(event, arg) = > {
  console.log('ping')
  event.sender.send('message-reply'.'pong') // return subroutine
})
// The main process sends messages to the renderer separately
win.webContents.send('message-reply'.'pong')
Copy the code

11. Packing problems

Reference: www.electron.build/configurati…

Configure the package configuration in vue.config.js using the nSIS package installation package for Windows programs

module.exports = {
  pluginOptions: {
    electronBuilder: {
      builderOptions: {
        win: {
          target: [{ target'nsis'.arch: ['ia32'.'x64']]}},nsis: {
          oneClickfalse.// One-click setup
          perMachinetrue.// Install for all users
          allowElevationtrue.// Allow permissions to be promoted. Set false to re-allow setup
          allowToChangeInstallationDirectorytrue.// Allows you to change the installation directory
          createDesktopShortcuttrue.// Create a desktop icon
          createStartMenuShortcuttrue.// Create start menu
          deleteAppDataOnUninstalltrue.include'./public/nsis/installer.nsh'.// The included script
          guid'53fe4cba-120d-4851-3cdc-dccb3a469019' / / software guid
        }
      }
    }
  }
}
Copy the code

12. Open the program from a web page

① Register the main process

App. RemoveAsDefaultProtocolClient (' testapp) app. SetAsDefaultProtocolClient (' testapp)Copy the code

(2) Add a configuration to the nSIS package configuration file (installer. NSH) to register the URL protocol in the registry during installation

! macro customInstall DetailPrint'Register testapp URI Handler'
  DeleteRegKey HKCR 'testapp'
  WriteRegStr HKCR 'testapp' ' ' 'URL:testapp'
  WriteRegStr HKCR 'testapp' 'URL Protocol' ' '
  WriteRegStr HKCR 'testapp\shell' ' ' ' '
  WriteRegStr HKCR 'testapp\shell\Open' ' ' ' '
  WriteRegStr HKCR 'testapp\shell\Open\command' ' ' '$INSTDIR\${APP_EXECUTABLE_FILENAME} %1'! macroendCopy the code

Testapp ://? Parameter = value

④ Get the parameters from the web page

// Handle the parameters passed in by the protocol when executing the page call application in the Window system
const handleArgvFromWeb = (argv) = > {
  console.log(argv)
  const url = argv.find(v= > v.indexOf(`${URLSCHEME}: / / `)! = = -1)
  console.log(url)
  if (url) handleUrlFromWeb(url)
}
// Handle url parameters from the web page, parameter customization, the following is an example
// The sample app url is testApp ://? token=205bdf49hc97ch4146h8124h8281a81fdcdb
const handleUrlFromWeb = (urlStr) = > {
  console.log(urlStr)
  const urlObj = new URL(urlStr)
  const { searchParams } = urlObj
  const token = searchParams.get('token')
  console.log(token)
}
Copy the code

You can see that the parameter is an array, so we need to get the last item

In production mode, if the software is not started in advance, you need to obtain parameters in the following figure when you start the software on the web page

If it is enabled in advance, it can be obtained in the condition judgment of judging singletons

13. The problem of slow download of the electron packet occurs during dependency installation or packaging

The root directory creates the.npmrc file

registry = https://registry.npm.taobao.org sass_binary_site = https://npm.taobao.org/mirrors/node-sass/ phantomjs_cdnurl  = http://cnpmjs.org/downloads electron_mirror = https://npm.taobao.org/mirrors/electron/ sqlite3_binary_host_mirror = https://foxgis.oss-cn-shanghai.aliyuncs.com/ profiler_binary_host_mirror = https://npm.taobao.org/mirrors/node-inspector/ chromedriver_cdnurl = https://cdn.npm.taobao.org/dist/chromedriverCopy the code

14. Open the link from your browser

const { shell } = require('electron')
shell.openExternal('https://www.bing.com')
Copy the code

15. In development mode, if the developer tool is enabled when opening the window and you want to close the window, you need to close the developer tool first to close the window

Before closing the window, check whether the developer tool is enabled. If so, close the developer tool first

if (callWin.isDevToolsOpened()) {
  callWin.closeDevTools()
}
Copy the code

16. Transparent window with no border, black border will appear when touching the edge of the screen

Reference: github.com/electron/el…

Basically you add a delay when you create a window,

setTimeout(() = > createWindow(), 400)
Copy the code

Then turn off hardware acceleration

app.disableHardwareAcceleration()
app.commandLine.appendSwitch('disable-gpu')
app.commandLine.appendSwitch('disable-software-rasterizer')
Copy the code

17. Transparent bezel-less window. When closing the developer tool, the background will turn white

Reference: github.com/electron/el…

When closing the developer tool, a new render view will be created, so the configured backgroundColor will be used. If not, the default white will be used, so you need to set the backgroundColor property to #00000000 when creating the window

The renderer gets the main process environment variables

Github.com/electron/el…

const { remote } = require('electron')
const envData = remote.getGlobal('process').env
Copy the code

19. The ASAR file is occupied

Vscode can be configured to ignore the dist_electron folder in setting.json

"files.exclude": {
  "dist_electron": true,}Copy the code

20. Software updates

Use the electron – updater

1. Configure vue.config.js to publish. After configuring the publish configuration, a fresh. yml file will be generated after the package is packed. You can also configure urls dynamically using autoupdater.setFeedURL (url)

pluginOptions: { electronBuilder: { builderOptions: { publish: [ { provider: 'generic', url: 'http://127.0.0.1:5000'}]}}}Copy the code

② Similar examples github.com/electron-us…

21. Electron Win7 problem

① Win7 SP1 or Win8 needed install KB4019990 patch to resolve this issue for now (note: None SP1 win7 needed to upgrade to SP1 before install the patch) github.com/electron/el…

② Upgrade.net github.com/electron/el…

③ Turn off hardware acceleration github.com/electron/el…

22. Unzip the ASAR plugin from 7Z

Currently, I can get an error when unpacking the asar command line, but I can get an error when unpacking the 7z plug-in completely.www.tc4shell.com/en/7zip/asa…

Download the DLL, copy it to the 7z installation directory and create a new oneFormatsfolder

Iv. Reference documents

  1. Vue – cli configuration
  2. Electron API documentation
  3. vue-cli-plugin-electron-builder
  4. Electron – build documentation
  5. Electron – updater document