Electron

Escrito em 22 de outubro de 2019 por Lucas Vieira
lucasvieira@protonmail.com

Sobre Electron

O que é Electron?

Tecnologia para criar aplicativos desktop cross-platform usando JavaScript, HTML, CSS.

  • Chromium + Node.js = Electron

A documentação pode ser encontrada em https://electronjs.org/docs.

Aplicativos feitos com Electron

  • Atom (editor de texto);
  • Brave (navegador web);
  • GitKraken;
  • Slack;
  • Visual Studio Code;
  • WordPress.com para Desktop.

Processos

Electron possui dois tipos de processos:

  • Processo principal: Script padrão do package.json. Cria instâncias de BrowserWindow para exibir páginas web.
  • Processos de renderização: Processo criado por cada página da web.

Criando o projeto

Instalação global do Electron

npm install -g electron

Após este processo, teremos o executável electron no path, utilizável via linha de comando.

Criação de um projeto com Electron

mkdir electron_app && cd electron_app
npm init
npm install --save electron

Na seção de scripts do arquivo package.json, coloque:

"scripts": {
    "start": "electron ."
},

Isto permitirá testar a aplicação com o comando npm start.

Arquivo index.js

Este é um arquivo básico que cria uma janela de 800x600, e renderiza a página index.html.

const {app, BrowserWindow} = require('electron');
const url  = require('url');
const path = require('path');

let window;

const createWindow = () => {
    window = new BrowserWindow({
        width:  800,
        height: 600,
        icon:   __dirname + "/img/app.png",
        webPreferences: {
            nodeIntegration: true,
        }
    });

    window.loadURL(url.format({
        pathname: path.join(__dirname, "index.html"),
        protocol: "file:",
        slashes:  true
    }));

    window.on('closed', () => {
        win = null;
    });
};

app.on("ready", createWindow);

app.on("window-all-closed", () => {
    if(process.platform !== 'darwin')
        app.quit();
});

Arquivo index.html

Esta é a página que será renderizada.

<!DOCTYPE html>
<html>
  <head>
    <meta charset='utf-8'>
  </head>
  <body>
    <h1>Olá, mundo!</h1>
    <p>Este é meu primeiro aplicativo Electron.</p>
  </body>
</html>

Bootstrap

Bootstrap é um framework para front-end livre e de código aberto, direcionado a desenvolvimento front-end responsivo e mobile-first.

Este framework possui templates de design para tipografia, formulários, botões, navegação e outros componentes de interface.

A documentação da versão 4.3 está aqui: https://getbootstrap.com/docs/4.3/getting-started/introduction/.

Usando Bootstrap

Instalando o Bootstrap localmente

Atualmente, o npm possui o Bootstrap v4.3.1 em seus repositórios.

npm install --save bootstrap

Incluindo o Bootstrap na página

Para utilizar o bootstrap, devemos incluir a folha de estilos bootstrap.min.css e o script bootstrap.min.js no arquivo index.html.

<!DOCTYPE html>
<html>
  <head>
    <meta charset='utf-8'>
    <!-- Folha de estilos do Bootstrap -->
    <link rel='stylesheet' href='node_modules/bootstrap/dist/css/bootstrap.min.css'>
  </head>
  <body>
    <header>
      <!-- Seção cinza com sombra regular -->
      <div class="bg-dark shadow">
        <section class="jumbotron text-center">
          <div class="container">
            <h1 class="jumbotron-heading">Olá, mundo!</h1>
            <p class="lead text-muted">
              Este é o meu primeiro aplicativo Electron.
            </p>
            <p>
              <!-- Botões -->
              <a class="btn btn-primary" href="#">Botão de ação primário</a>
              <a class="btn btn-secondary" href="#">Botão de ação secundário</a>
            </p>
        </section>
        </div>
    </header>
    <!-- Script do Bootstrap -->
    <script src='node_modules/bootstrap/dist/js/bootstrap.min.js'></script>
  </body>
</html>

Comunicando a página com o Node

Arquivo index.js

Para realizar a comunicação entre o processo principal e os processos de renderização, utilizamos o módulo de IPC (Inter-process Communication) do Electron.

const {app, BrowserWindow} = require('electron');
const url  = require('url');
const path = require('path');

const { ipcMain } = require('electron'); // Importação do IPC

let window;

const createWindow = () => {
    window = new BrowserWindow({
        width:  800,
        height: 600,
        icon:   __dirname + "/img/app.png",
        webPreferences: {
            nodeIntegration: true,
        }
    });

    window.loadURL(url.format({
        pathname: path.join(__dirname, "index.html"),
        protocol: "file:",
        slashes:  true
    }));

    window.on('closed', () => {
        win = null;
    });
};

app.on("ready", createWindow);

app.on("window-all-closed", () => {
    if(process.platform !== 'darwin')
        app.quit();
});


// Exportando um evento de clique para a
// comunicação interprocessual
ipcMain.on('click', () => {
    console.log('Olá a partir do bootstrap!');
});

Arquivo renderer.js

Este novo arquivo será o script da página HTML, que importará o Electron e atrelará o evento de clique exportado ao elemento com ID igual a say-hi.

const { ipcRenderer } = require('electron');

document.querySelector('#say-hi')
    .addEventListener('click', () => {
        ipcRenderer.send('click');
    });

Arquivo index.html

Nossa página agora possuirá um botão com a ID igual a say-hi, e incluiremos o script do processo de renderização.

<!DOCTYPE html>
<html>
  <head>
    <meta charset='utf-8'>
    <link rel='stylesheet' href='node_modules/bootstrap/dist/css/bootstrap.min.css'>
  </head>
  <body>
    <header>
      <div class="bg-dark shadow">
        <section class="jumbotron text-center">
          <div class="container">
            <h1 class="jumbotron-heading">Olá, mundo!</h1>
            <p class="lead text-muted">
              Este é o meu primeiro aplicativo Electron.
            </p>
            <p>
              <!-- Mudança no ID do botão -->
              <a id="say-hi" class="btn btn-primary" href="#">Botão de ação primário</a>
              
              <a class="btn btn-secondary" href="#">Botão de ação secundário</a>
            </p>
        </section>
        </div>
    </header>
    <!-- Script do processo de renderização -->
    <script src='./renderer.js'></script>
    <script src='node_modules/bootstrap/dist/js/bootstrap.min.js'></script>
  </body>
</html>

De volta à página anterior