diff --git a/.gitmodules b/.gitmodules
new file mode 100644
index 00000000..b4a5a6c1
--- /dev/null
+++ b/.gitmodules
@@ -0,0 +1,3 @@
+[submodule "zmodemjs"]
+ path = demo/zmodemjs
+ url = https://github.com/FGasper/zmodemjs.git
diff --git a/demo/app.js b/demo/app.js
index 8637dad8..089ccf6e 100644
--- a/demo/app.js
+++ b/demo/app.js
@@ -21,6 +21,10 @@ app.get('/main.js', function(req, res){
res.sendFile(__dirname + '/main.js');
});
+app.get('/zmodemjs/*.js', function(req, res){
+ res.sendFile(__dirname + req.url);
+});
+
app.post('/terminals', function (req, res) {
var cols = parseInt(req.query.cols),
rows = parseInt(req.query.rows),
@@ -59,6 +63,7 @@ app.ws('/terminals/:pid', function (ws, req) {
ws.send(logs[term.pid]);
term.on('data', function(data) {
+console.log("From PTY: ", escape(data) );
try {
ws.send(data);
} catch (ex) {
diff --git a/demo/index.html b/demo/index.html
index daa60b6f..60d0b376 100644
--- a/demo/index.html
+++ b/demo/index.html
@@ -12,9 +12,57 @@
+
+
+
+
+
+
+
+
+
+
xterm.js: xterm, in the browser
+
+
+
+
+
+
Name:
+
Size:
+
Last modified:
+
Mode:
+
Files remaining:
+
Bytes remaining:
+
+
+
+
+
+
+
+
+
Actions
diff --git a/demo/main.js b/demo/main.js
index f4fb0a2a..c1d4d4e9 100644
--- a/demo/main.js
+++ b/demo/main.js
@@ -90,7 +90,7 @@ function createTerminal() {
socketURL = protocol + location.hostname + ((location.port) ? (':' + location.port) : '') + '/terminals/';
term.open(terminalContainer);
- term.fit();
+ //term.fit();
// fit is called within a setTimeout, cols and rows need this.
setTimeout(() => {
@@ -109,13 +109,160 @@ function createTerminal() {
socket.onopen = runRealTerminal;
socket.onclose = runFakeTerminal;
socket.onerror = runFakeTerminal;
+
+ socket.addEventListener("message", handleWSMessage);
});
});
}, 0);
}
+var text_encoder = new TextEncoder();
+var zsentry = new Zmodem.Sentry();
+
+var zsession;
+function handleWSMessage(evt) {
+ var binary = text_encoder.encode(evt.data);
+ var input = Array.prototype.slice.call( new Uint8Array(binary) );
+console.log("from WS", evt.data, input, evt.data.charCodeAt( evt.data.length - 2 ));
+
+ if (zsession) {
+ zsession.consume(input);
+ if (zsession.has_ended()) {
+ input = zsession.get_trailing_bytes();
+ zsession = null;
+ }
+ }
+ else {
+ let termbytes;
+ [termbytes, zsession] = zsentry.parse(input);
+ input = termbytes;
+
+ if (zsession) {
+
+ zsession.set_sender( (octets) => {
+ socket.send( String.fromCharCode.apply(String, octets) );
+ } );
+
+ var start_form = document.getElementById("zm_start");
+ start_form.style.display = "";
+ start_form.onsubmit = function(e) {
+ start_form.style.display = "none";
+
+ if (zsession.type === "receive") {
+ zsession.on("offer", function(xfer) {
+ _show_file_info(xfer);
+
+ var offer_form = document.getElementById("zm_offer");
+ offer_form.style.display = "";
+ offer_form.onsubmit = function(e) {
+ offer_form.style.display = "none";
+
+ if (offer_form.zmaccept) {
+ var FILE_BUFFER = [];
+ xfer.on("input", (payload) => {
+ _update_progress(xfer);
+ FILE_BUFFER.push.apply(FILE_BUFFER, payload);
+ });
+ xfer.accept().then( () => {
+ _download(xfer, FILE_BUFFER);
+ _hide_file_info();
+ } );
+ }
+ else {
+ _hide_file_info();
+ xfer.skip();
+ }
+ };
+ } );
+
+ zsession.start();
+ }
+ else {
+ var choose_form = document.getElementById("zm_choose");
+ choose_form.style.display = "";
+ choose_form.onsubmit = function(e) {
+ choose_form.style.display = "none";
+
+ var file_el = document.getElementById("zm_files");
+ var batch = [];
+ var total_size = 0;
+ for (var f=0; f {
+ if (xfer === undefined) {
+ return promise_callback(); //skipped
+ }
+
+ return new Promise( (res) => {
+ var reader = new FileReader();
+ reader.onerror = function(e) {
+ console.error("file read error", e);
+ throw("File read error: " + e);
+ };
+
+ var offset = xfer.get_offset();
+ reader.onprogress = function(e) {
+ xfer.send(
+ new Uint8Array(e.target.result, offset)
+ );
+ offset = e.loaded;
+ };
+
+ reader.onload = function(e) {
+ xfer.end(
+ new Uint8Array(e.target.result, offset)
+ ).then(res).then(promise_callback);
+ };
+
+ reader.readAsArrayBuffer(cur_b.obj);
+ } );
+ } )
+ }
+ else {
+ zsession.close();
+ choose_form.style.display = "none";
+ }
+ }
+
+ promise_callback();
+ };
+
+ }
+ };
+ }
+ }
+
+ if (input.length) {
+ term.write(
+ String.fromCharCode.apply(String, input)
+ );
+ }
+}
+
+//var text_encoder = new TextEncoder();
+
function runRealTerminal() {
- term.attach(socket);
+ //term.attach(socket);
+
+ term.on("data", (d) => {
+ //socket.send( text_encoder.encode(d) );
+ socket.send(d);
+ });
+
term._initialized = true;
}
diff --git a/demo/zmodemjs b/demo/zmodemjs
new file mode 160000
index 00000000..eefc61c2
--- /dev/null
+++ b/demo/zmodemjs
@@ -0,0 +1 @@
+Subproject commit eefc61c2c4cbad743dea53b417a4948a08b7b652