ngx javascript typescript angular ipc electron

javascript - ngx - angular electron



¿Cómo integrar Electron ipcRenderer en la aplicación Angular 2 basada en TypeScript? (6)

Quiero usar ipcMain / ipcRenderer en mi proyecto para comunicarme de Angular a Electron y viceversa.

El lado del electrón es bastante claro:

const electron = require(''electron''), ipcMain = electron.ipcMain, ; ipcMain.on(''asynchronous-message'', function(event, arg) { console.debug(''ipc.async'', arg); event.sender.send(''asynchronous-reply'', ''async-pong''); }); ipcMain.on(''synchronous-message'', function(event, arg) { console.debug(''ipc.sync'', arg); event.returnValue = ''sync-pong''; });

Pero no tengo idea de cómo integrar ese módulo de Electron en mi aplicación Angular 2. Uso SystemJS como cargador de módulos, pero soy un novato con él.

Cualquier ayuda apreciada. Gracias.

--- Mario


Hay conflicto, porque Electron utiliza la resolución del módulo commonjs , pero su código ya está compilado con las reglas de systemjs .

Dos soluciones:

Manera robusta . Registrar objeto require devuelto:

<script> System.set(''electron'', System.newModule(require(''electron''))); </script>

Esto es lo mejor, porque el script renderer/init.js carga ese módulo en el inicio. SystemJS tiene que tomarlo solo, no cargas.

Vía alternativa . Usa el truco sucio con la declaración.

Obtener instancia electrónica dentro de index.html :

<script> var electron = require(''electron''); </script>

Decláralo dentro de tu archivo typescript esta manera:

declare var electron: any;

Úsalo con libertad.

electron.ipcRenderer.send(...)


Pero no tengo idea de cómo integrar ese módulo de Electron en mi aplicación Angular 2

Habría alojado angular dentro del proceso de renderizado UI en electrón. El ipcMain se utiliza para comunicarse con procesos secundarios que no se procesan.


Esto debería ser solo un caso de requerir el módulo ipcRenderer en su archivo html principal (electron lo proporcionará para usted):

<script> var ipc = require(''electron'').ipcRenderer; var response = ipc.sendSync(''getSomething''); console.log(response); // prints ''something'' </script>

y luego configurando un controlador en su archivo js principal:

const ipcMain = require(''electron'').ipcMain; ipcMain.on(''getSomething'', function(event, arg) { event.returnValue = ''something''; });

Eso es todo lo que debería haber en ello.


Mi solución:

configurar una baseUrl en tsconfig.json

en la raíz del directorio señalado por la baseUrl, cree un directorio "electron". Dentro de este directorio, un archivo index.ts:

const electron = (<any>window).require(''electron''); export const {BrowserWindowProxy} = electron; export const {desktopCapturer} = electron; export const {ipcRenderer} = electron; export const {remote} = electron; export const {webFrame} = electron;

(lo ideal sería exportar [...] por defecto (''electrón''), pero esto no es analizable estáticamente ...)

Ahora puedo tener en mi proceso de renderizador:

import {remote} from ''electron''; console.log(remote);

Espero que tenga sentido ...

con mecanografía habilitada:

///<reference path="../../typings/globals/electron/index.d.ts"/> const electron = (<any>window).require(''electron''); export const BrowserWindowProxy = <Electron.BrowserWindowProxy>electron.BrowserWindowProxy; export const desktopCapturer = <Electron.DesktopCapturer>electron.desktopCapturer; export const ipcRenderer = <Electron.IpcRenderer>electron.ipcRenderer; export const remote = <Electron.Remote>electron.remote; export const webFrame = <Electron.WebFrame>electron.webFrame;

NB: tipificaciones que tengo es de:

{ "globalDependencies": { "electron": "registry:dt/electron#1.4.8+20161220141501" } }


Un paquete reciente llamado ngx-electron hace fácil. Enlace al repositorio y enlace al artículo.

src / app / app.module.ts

import { NgxElectronModule } from ''ngx-electron''; // other imports @NgModule({ imports: [NgxElectronModule], ... })

src / app / your.component.ts

import { Component, NgZone } from ''@angular/core''; import { ElectronService } from ''ngx-electron''; @Component({ selector: ''app-your'', templateUrl: ''your.component.html'' }) export class YourComponent { message: string; constructor(private _electronService: ElectronService, private _ngZone: NgZone) { this._electronService.ipcRenderer.on(''asynchronous-reply'', (event, arg) => { this._ngZone.run(() => { let reply = `Asynchronous message reply: ${arg}`; this.message = reply; }); } } playPingPong() { this._electronService.ipcRenderer.send(''asynchronous-message'', ''ping''); } }

Nota: se utiliza this.message porque este this.message se actualiza de forma asíncrona fuera de la zona de Angular. article


Componente.TS

const ipc = require(''electron'').ipcRenderer; @Component({ selector: ''app-my component'',..... })

....

public testElectronIpc(): void{ ipc.send(''test-alert''); }

MAIN.JS

// IPC message listeners ipc.on(''test-alert'', function (event, arg) { console.log(''Test alert received from angular component''); })

configuración

plugins: [new webpack.ExternalsPlugin (''commonjs'', [''desktop-capturer'', ''electron'', ''ipc'', ''ipc-renderer'', ''native-image'', ''remote'', ''web-frame'', '' portapapeles '','' crash-reporter '','' screen '','' shell ''])],