Unfinished websocket demo
This commit is contained in:
parent
7a39c7e483
commit
9680949503
42
test.html
42
test.html
|
@ -1,42 +0,0 @@
|
||||||
<!DOCTYPE html>
|
|
||||||
<html>
|
|
||||||
<head>
|
|
||||||
<title>WebSocket test</title>
|
|
||||||
</head>
|
|
||||||
<body>
|
|
||||||
<script>
|
|
||||||
function hex(str)
|
|
||||||
{
|
|
||||||
var arr1 = [];
|
|
||||||
for (var n = 0, l = str.length; n < l; n ++)
|
|
||||||
{
|
|
||||||
var hex = Number(str.charCodeAt(n)).toString(16);
|
|
||||||
arr1.push(hex);
|
|
||||||
}
|
|
||||||
return arr1.join(' ');
|
|
||||||
}
|
|
||||||
|
|
||||||
var ws = new WebSocket("ws://127.0.0.1:7767/"),
|
|
||||||
messages = document.createElement('ul');
|
|
||||||
ws.onmessage = function (event) {
|
|
||||||
var messages = document.getElementsByTagName('ul')[0],
|
|
||||||
message = document.createElement('li'),
|
|
||||||
res = new Response(event.data).arrayBuffer().then(
|
|
||||||
function(buff) {
|
|
||||||
last = buff;
|
|
||||||
data = new DataView(buff);
|
|
||||||
|
|
||||||
data_str = "";
|
|
||||||
for (let i = 0; i < data.byteLength; i++)
|
|
||||||
data_str += String.fromCharCode(data.getInt8(i));
|
|
||||||
|
|
||||||
content = document.createTextNode(data_str + " | " + hex(data_str));
|
|
||||||
message.appendChild(content);
|
|
||||||
messages.appendChild(message);
|
|
||||||
}
|
|
||||||
);
|
|
||||||
};
|
|
||||||
document.body.appendChild(messages);
|
|
||||||
</script>
|
|
||||||
</body>
|
|
||||||
</html>
|
|
115
www/js/fly-ws.js
Normal file
115
www/js/fly-ws.js
Normal file
|
@ -0,0 +1,115 @@
|
||||||
|
class FLYSocket {
|
||||||
|
constructor(ws,
|
||||||
|
callbackData = this.callbackDummy,
|
||||||
|
callbackRaw = this.callbackDummy) {
|
||||||
|
this.ws = new WebSocket(ws);
|
||||||
|
this.pointer = 0;
|
||||||
|
|
||||||
|
this.callbackData = callbackData;
|
||||||
|
this.callbackRaw = callbackRaw;
|
||||||
|
|
||||||
|
this.ws.onmessage = this.onMessage.bind(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
onMessage(e) {
|
||||||
|
new Response(event.data).arrayBuffer().then(
|
||||||
|
function(buff) {
|
||||||
|
let data = new DataView(buff);
|
||||||
|
this.callbackRaw(data);
|
||||||
|
|
||||||
|
if (this.callbackData != this.callbackDummy || true) { // DEBUG
|
||||||
|
this.callbackData( this.parse(data) );
|
||||||
|
}
|
||||||
|
}.bind(this)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
parse(data) {
|
||||||
|
window.data = data; // DEBUG
|
||||||
|
let packets = [];
|
||||||
|
this.pointer = 0;
|
||||||
|
|
||||||
|
while (this.pointer < data.byteLength) {
|
||||||
|
let packetID = data.getInt8(this.pointer++);
|
||||||
|
packets.push({
|
||||||
|
packetID: packetID,
|
||||||
|
value: (this["handle_packet" + packetID] || this.handle_packetInvalid)(data)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
return packets;
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packet0(data) {
|
||||||
|
// BxI
|
||||||
|
// B: Length
|
||||||
|
// I: FlightUUID
|
||||||
|
let ret = [];
|
||||||
|
let length = data.getUint8(this.pointer++);
|
||||||
|
for (let i = 0; i < length; i++) {
|
||||||
|
ret.push( data.getUint16(this.pointer) );
|
||||||
|
this.pointer += 2;
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packet1(data) {
|
||||||
|
// ?
|
||||||
|
// ?: Subscribed to changes
|
||||||
|
return data.getUint8(this.pointer++) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packet2(data) {
|
||||||
|
// I?
|
||||||
|
// I: FlightUUID
|
||||||
|
// ?: Subscribed to flight data
|
||||||
|
let ret = [];
|
||||||
|
ret.push( data.getUint16(this.pointer) ); this.pointer += 2;
|
||||||
|
ret.push( data.getUint8(this.pointer++) != 0 );
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packet3(data) { // TODO: implement (Whole data / history)
|
||||||
|
// Ixs
|
||||||
|
// I: Length
|
||||||
|
// s: DataStream
|
||||||
|
return ret = [];
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packet4(data) {
|
||||||
|
// I?
|
||||||
|
// I: FlightUUID
|
||||||
|
// ?: Flight active
|
||||||
|
let ret = [];
|
||||||
|
ret.push( data.getUint16(this.pointer) ); this.pointer += 2;
|
||||||
|
ret.push( data.getUint8(this.pointer++) != 0 );
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packet5(data) { // TODO: implement (One frame)
|
||||||
|
// Ixs
|
||||||
|
// I: Length
|
||||||
|
// s: DataStream
|
||||||
|
}
|
||||||
|
|
||||||
|
handle_packetInvalid(data) {
|
||||||
|
throw TypeError(`Invalid DATA: ${Array.from( this.buffer2HexArray(data, --this.pointer) ).join(" ")}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
*buffer2HexArray(buff, start = 0, end = buff.byteLength) {
|
||||||
|
for (let i = start; i < end; i++) {
|
||||||
|
yield hex.push( buff.getUint8(i).toString(16) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
callbackDummy(_) {}
|
||||||
|
}
|
||||||
|
|
||||||
|
class Flight {
|
||||||
|
constructor(uuid) {
|
||||||
|
this.uuid = uuid;
|
||||||
|
this.playername;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log("OK") // TODO: please remove...
|
21
www/js/struct/LICENSE
Normal file
21
www/js/struct/LICENSE
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
The MIT License (MIT)
|
||||||
|
|
||||||
|
Copyright (c) 2016 Aksel Jensen (TheRealAksel at github)
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
60
www/js/struct/struct.js
Normal file
60
www/js/struct/struct.js
Normal file
|
@ -0,0 +1,60 @@
|
||||||
|
// https://github.com/lyngklip/structjs
|
||||||
|
"use strict"
|
||||||
|
const rechk = /^([<>])?(([1-9]\d*)?([xcbB?hHiIfdsp]))*$/
|
||||||
|
const refmt = /([1-9]\d*)?([xcbB?hHiIfdsp])/g
|
||||||
|
const str = (v,o,c) => String.fromCharCode(
|
||||||
|
...new Uint8Array(v.buffer, v.byteOffset + o, c))
|
||||||
|
const rts = (v,o,c,s) => new Uint8Array(v.buffer, v.byteOffset + o, c)
|
||||||
|
.set(s.split('').map(str => str.charCodeAt(0)))
|
||||||
|
const pst = (v,o,c) => str(v, o + 1, Math.min(v.getUint8(o), c - 1))
|
||||||
|
const tsp = (v,o,c,s) => { v.setUint8(o, s.length); rts(v, o + 1, c - 1, s) }
|
||||||
|
const lut = le => ({
|
||||||
|
x: c=>[1,c,0],
|
||||||
|
c: c=>[c,1,o=>({u:v=>str(v, o, 1) , p:(v,c)=>rts(v, o, 1, c) })],
|
||||||
|
'?': c=>[c,1,o=>({u:v=>Boolean(v.getUint8(o)),p:(v,B)=>v.setUint8(o,B)})],
|
||||||
|
b: c=>[c,1,o=>({u:v=>v.getInt8( o ), p:(v,b)=>v.setInt8( o,b )})],
|
||||||
|
B: c=>[c,1,o=>({u:v=>v.getUint8( o ), p:(v,B)=>v.setUint8( o,B )})],
|
||||||
|
h: c=>[c,2,o=>({u:v=>v.getInt16( o,le), p:(v,h)=>v.setInt16( o,h,le)})],
|
||||||
|
H: c=>[c,2,o=>({u:v=>v.getUint16( o,le), p:(v,H)=>v.setUint16( o,H,le)})],
|
||||||
|
i: c=>[c,4,o=>({u:v=>v.getInt32( o,le), p:(v,i)=>v.setInt32( o,i,le)})],
|
||||||
|
I: c=>[c,4,o=>({u:v=>v.getUint32( o,le), p:(v,I)=>v.setUint32( o,I,le)})],
|
||||||
|
f: c=>[c,4,o=>({u:v=>v.getFloat32(o,le), p:(v,f)=>v.setFloat32(o,f,le)})],
|
||||||
|
d: c=>[c,8,o=>({u:v=>v.getFloat64(o,le), p:(v,d)=>v.setFloat64(o,d,le)})],
|
||||||
|
s: c=>[1,c,o=>({u:v=>str(v,o,c), p:(v,s)=>rts(v,o,c,s.slice(0,c ) )})],
|
||||||
|
p: c=>[1,c,o=>({u:v=>pst(v,o,c), p:(v,s)=>tsp(v,o,c,s.slice(0,c - 1) )})]
|
||||||
|
})
|
||||||
|
const errbuf = new RangeError("Structure larger than remaining buffer")
|
||||||
|
const errval = new RangeError("Not enough values for structure")
|
||||||
|
const struct = format => {
|
||||||
|
let fns = [], size = 0, m = rechk.exec(format)
|
||||||
|
if (!m) { throw new RangeError("Invalid format string") }
|
||||||
|
const t = lut('<' === m[1]), lu = (n, c) => t[c](n ? parseInt(n, 10) : 1)
|
||||||
|
while ((m = refmt.exec(format))) { ((r, s, f) => {
|
||||||
|
for (let i = 0; i < r; ++i, size += s) { if (f) {fns.push(f(size))} }
|
||||||
|
})(...lu(...m.slice(1)))}
|
||||||
|
const unpack_from = (arrb, offs) => {
|
||||||
|
if (arrb.byteLength < (offs|0) + size) { throw errbuf }
|
||||||
|
let v = new DataView(arrb, offs|0)
|
||||||
|
return fns.map(f => f.u(v))
|
||||||
|
}
|
||||||
|
const pack_into = (arrb, offs, ...values) => {
|
||||||
|
if (values.length < fns.length) { throw errval }
|
||||||
|
if (arrb.byteLength < offs + size) { throw errbuf }
|
||||||
|
const v = new DataView(arrb, offs)
|
||||||
|
new Uint8Array(arrb, offs, size).fill(0)
|
||||||
|
fns.forEach((f, i) => f.p(v, values[i]))
|
||||||
|
}
|
||||||
|
const pack = (...values) => {
|
||||||
|
let b = new ArrayBuffer(size)
|
||||||
|
pack_into(b, 0, ...values)
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
const unpack = arrb => unpack_from(arrb, 0)
|
||||||
|
function* iter_unpack(arrb) {
|
||||||
|
for (let offs = 0; offs + size <= arrb.byteLength; offs += size) {
|
||||||
|
yield unpack_from(arrb, offs);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return Object.freeze({
|
||||||
|
unpack, pack, unpack_from, pack_into, iter_unpack, format, size})
|
||||||
|
}
|
164
www/main.html
Normal file
164
www/main.html
Normal file
|
@ -0,0 +1,164 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<title>WebSocket DEMO</title>
|
||||||
|
<script src="js/struct/struct.js"></script>
|
||||||
|
<script src="js/fly-ws.js"></script>
|
||||||
|
<style>
|
||||||
|
html, body {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
top: 0px;
|
||||||
|
left: 0px;
|
||||||
|
margin: 0px;
|
||||||
|
display: grid;
|
||||||
|
background: #141414;
|
||||||
|
color: #e7e7e7;
|
||||||
|
}
|
||||||
|
|
||||||
|
body {
|
||||||
|
grid-template: 100px 50px repeat(4, 1fr) / 50px calc(100vh - 150px) calc((100vh - 150px) / 4) 1fr;
|
||||||
|
grid-template-areas: "title title title console"
|
||||||
|
"ws-status ws-input ws-connect console"
|
||||||
|
". map data-al console"
|
||||||
|
". map data-sp console"
|
||||||
|
". map data-ps console"
|
||||||
|
". map data-hp console";
|
||||||
|
}
|
||||||
|
|
||||||
|
body > div {
|
||||||
|
display: grid;
|
||||||
|
}
|
||||||
|
|
||||||
|
.title {
|
||||||
|
align-self: center;
|
||||||
|
justify-self: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ws {
|
||||||
|
align-self: center;
|
||||||
|
height: 30px;
|
||||||
|
}
|
||||||
|
.ws > * {
|
||||||
|
font-size: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.border {
|
||||||
|
border: 1px solid dimgray;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ws-status {
|
||||||
|
justify-self: center;
|
||||||
|
width: 30px;
|
||||||
|
background: gray;
|
||||||
|
}
|
||||||
|
.online {
|
||||||
|
background: lime;
|
||||||
|
}
|
||||||
|
.offline {
|
||||||
|
background: red;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ws-connect {
|
||||||
|
justify-self: start;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Yea... im seperating this */
|
||||||
|
.title {
|
||||||
|
grid-area: title;
|
||||||
|
}
|
||||||
|
.ws-status {
|
||||||
|
grid-area: ws-status;
|
||||||
|
}
|
||||||
|
.ws-input {
|
||||||
|
grid-area: ws-input;
|
||||||
|
}
|
||||||
|
.ws-connect {
|
||||||
|
grid-area: ws-connect;
|
||||||
|
}
|
||||||
|
.console {
|
||||||
|
grid-area: console;
|
||||||
|
}
|
||||||
|
.map {
|
||||||
|
grid-area: map;
|
||||||
|
}
|
||||||
|
.data-al {
|
||||||
|
grid-area: data-al;
|
||||||
|
}
|
||||||
|
.data-sp {
|
||||||
|
grid-area: data-sp;
|
||||||
|
}
|
||||||
|
.data-ps {
|
||||||
|
grid-area: data-ps;
|
||||||
|
}
|
||||||
|
.data-hp {
|
||||||
|
grid-area: data-hp;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="title">
|
||||||
|
<h1>Websocket DEMO</h1>
|
||||||
|
</div>
|
||||||
|
<div class="ws ws-status border"></div>
|
||||||
|
<div class="ws ws-input">
|
||||||
|
<input id="addr" value="ws://127.0.0.1:7767"/>
|
||||||
|
</div>
|
||||||
|
<div class="ws ws-connect">
|
||||||
|
<button onclick="connect()">Connect</button>
|
||||||
|
</div>
|
||||||
|
<div class="map border"></div>
|
||||||
|
<div class="data-al border"></div>
|
||||||
|
<div class="data-sp border"></div>
|
||||||
|
<div class="data-ps border"></div>
|
||||||
|
<div class="data-hp border"></div>
|
||||||
|
<div class="console border" id="stdout"></div>
|
||||||
|
<script>
|
||||||
|
var fs;
|
||||||
|
|
||||||
|
function connect() {
|
||||||
|
fs = new FLYSocket(
|
||||||
|
addr.value, // websocket addr
|
||||||
|
// callbackData
|
||||||
|
// callbackRaw
|
||||||
|
);
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
<!--
|
||||||
|
<script>
|
||||||
|
function hex(str)
|
||||||
|
{
|
||||||
|
var arr1 = [];
|
||||||
|
for (var n = 0, l = str.length; n < l; n ++)
|
||||||
|
{
|
||||||
|
var hex = Number(str.charCodeAt(n)).toString(16);
|
||||||
|
arr1.push(hex);
|
||||||
|
}
|
||||||
|
return arr1.join(' ');
|
||||||
|
}
|
||||||
|
|
||||||
|
var ws = new WebSocket("ws://127.0.0.1:7767/"),
|
||||||
|
messages = document.createElement('ul');
|
||||||
|
ws.onmessage = function (event) {
|
||||||
|
var messages = document.getElementsByTagName('ul')[0],
|
||||||
|
message = document.createElement('li'),
|
||||||
|
res = new Response(event.data).arrayBuffer().then(
|
||||||
|
function(buff) {
|
||||||
|
last = buff;
|
||||||
|
data = new DataView(buff);
|
||||||
|
|
||||||
|
data_str = "";
|
||||||
|
for (let i = 0; i < data.byteLength; i++)
|
||||||
|
data_str += String.fromCharCode(data.getInt8(i));
|
||||||
|
|
||||||
|
content = document.createTextNode(data_str + " | " + hex(data_str));
|
||||||
|
message.appendChild(content);
|
||||||
|
messages.appendChild(message);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
};
|
||||||
|
document.body.appendChild(messages);
|
||||||
|
</script>-->
|
||||||
|
</body>
|
||||||
|
</html>
|
Loading…
Reference in New Issue
Block a user