I am trying to create a terminal in my Electron app (similar to the one in vscode).
When I try to send the data that is created when the terminal (with win.webContents.send()
an error occurs)
How can I send the data back to the renderer without this error occurring?
I am not sure what to do as I don't have much experience in node-pty/electron.
Any help is appreciated. Thank you!
Error:
Main process:
const { app, BrowserWindow, ipcMain } = require('electron')
const path = require("path")
require('@electron/remote/main').initialize()
const createMainWindow = () => {
const win = new BrowserWindow({
width: 1920,
height: 1080,
webPreferences: {
nodeIntegration: true,
contextIsolation: false,
enableRemoteModule: true,
devTools: true
},
resizable: true,
frame: false,
devTools: true,
contextIsolation: false,
enableRemoteModule: true,
//icon: path.join(__dirname + '/relico.ico'),
})
win.loadFile('./page-app/index.html')
require('@electron/remote/main').enable(win.webContents)
}
const createLoaderWindow = () => {
const win = new BrowserWindow({
width: 300,
height: 400,
webPreferences: {
nodeIntegration: true,
contextIsolation: false,
enableRemoteModule: true,
devTools: true
},
resizable: false,
frame: false,
devTools: true,
contextIsolation: false,
enableRemoteModule: true,
//icon: path.join(__dirname + '/relico.ico'),
})
win.loadFile('./page-app/loader.html')
const pty = require("node-pty");
const os = require("os");
var shell = os.platform() === "win32" ? "powershell.exe" : "bash";
var ptyProcess = pty.spawn(shell, [], {
name: "xterm-color",
cols: 80,
rows: 30,
cwd: process.env.HOME,
env: process.env
});
ptyProcess.onData((data) => {
process.stdout.write(data);
win.webContents.send('terminal.incomingData', data);
});
ipcMain.on("terminal.keystroke", (event, key) => {
console.log("KEY:", key)
ptyProcess.write(key);
});
require('@electron/remote/main').enable(win.webContents)
}
app.whenReady().then(createLoaderWindow)
ipcMain.handle('openMain', async () => {
createMainWindow();
return true;
})
Render process:
const { Terminal } = require('xterm');
const { FitAddon } = require('xterm-addon-fit');
const { WebLinksAddon } = require('xterm-addon-web-links');
const os = require('os');
var term = new Terminal({
cursorBlink: true,
fontFamily: 'monospace',
fontSize: 14,
lineHeight: 1.4,
scrollback: 1000,
});
term.open(document.getElementById('terminal'));
ipcRenderer.on("terminal.incomingData", (event, data) => {
console.log("INCOMING:")
console.dir(data);
term.write(data);
});
term.onData(e => {
console.dir(e)
ipcRenderer.send("terminal.keystroke", e);
});
I figured it out now.
I was applying this code:
const pty = require("node-pty");
const os = require("os");
var shell = os.platform() === "win32" ? "powershell.exe" : "bash";
var ptyProcess = pty.spawn(shell, [], {
name: "xterm-color",
cols: 80,
rows: 30,
cwd: process.env.HOME,
env: process.env
});
ptyProcess.onData((data) => {
process.stdout.write(data);
win.webContents.send('terminal.incomingData', data);
});
ipcMain.on("terminal.keystroke", (event, key) => {
console.log("KEY:", key)
ptyProcess.write(key);
});
To the loader window, rather than the main window. When the loader window was closed, the loader window as receiving the message, rather than the main window.