Проблема с интеграцией node-pty и Xterm JS с VueJS в приложении Electron - PullRequest
2 голосов
/ 20 января 2020

Я пытался интегрировать node-pty и xterm js в электронное приложение. Я использую VueJS для внешнего интерфейса и хочу создать интерфейс терминала внутри приложения. Итак, как мне структурировать мой код так, чтобы я мог использовать его в качестве компонента, подобного этому:

<Terminal></Terminal>

Я пробовал следующее, но не смог заставить его работать полностью.

// Terminal.vue component.

<template>
  <v-container fluid class="pa-1">
    <div style="overflow-y:scroll!important" class="pa-1 black" id="terminal"></div>
  </v-container>
</template>

<script>
import "xterm/css/xterm.css";
import { Terminal } from "xterm";
import { FitAddon } from "xterm-addon-fit";

const os = require("os");
const pty = require("node-pty");

const shell = process.env[os.platform() === "win32" ? "COMSPEC" : "SHELL"];

const ptyProc = pty.spawn(shell, [], {
  name: "xterm-color",
  env: process.env
});

const term = new Terminal({
  rows: 40,
  experimentalCharAtlas: "dynamic"
});

const fitAddon = new FitAddon();

term.loadAddon(fitAddon);

export default {
  data() {
    return {
      term: null
    };
  },

  mounted() {
    console.log("entered");

    term.open(document.getElementById("terminal"));

    fitAddon.fit();

    term.onData(data => ptyProc.write(data));
    ptyProc.on("data", function(data) {
      console.log(data);
      term.write(data);
    });

    term.onResize(size => {
      ptyProc.resize(
        Math.max(size ? size.cols : term.cols, 1),
        Math.max(size ? size.rows : term.rows, 1)
      );
    });

    console.log("exiting...");
  }
};
</script>

Используя приведенный выше код, я получил следующий интерфейс:

Интерфейс терминала

Здесь много функций, таких как история терминала, цвета, некоторые сокращения не работают, которые работают нормально с реализацией vanilla javascript ниже:

const {Terminal} = require('xterm');
const os = require('os');
const pty = require('node-pty');
const {FitAddon} = require('xterm-addon-fit');

const shell = process.env[os.platform() === 'win32' ? 'COMSPEC' : 'SHELL'];

const ptyProc = pty.spawn(shell, [], {
    name: 'xterm-color',
    env: process.env
});

const term = new Terminal({
    experimentalCharAtlas: 'dynamic',
    rows: 42
});

const fitAddon = new FitAddon();

term.loadAddon(fitAddon);
term.open(document.getElementById('opt1-panel'));
fitAddon.fit();

term.onData(data => ptyProc.write(data));
ptyProc.on('data', function(data){
    term.write(data);
});

term.onResize(size => {
    ptyProc.resize(
        Math.max(size ? size.cols : term.cols, 1),
        Math.max(size ? size.rows : term.rows, 1)
    );
});

На следующем рисунке показан результат кода выше, который представляет собой другой проект без vuejs. Использование обычного JS

Так как я могу заставить его работать в vuejs.

Только что начал изучать VueJS и веб-материал, поэтому, извините, если его что-то очевидное.

...