forked from Yrr0r/paperang-web
-
Notifications
You must be signed in to change notification settings - Fork 0
/
script.js
194 lines (171 loc) · 5.87 KB
/
script.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
var btservice;
var sockchar;
var notify;
// some global variables:
var widthbyte = 48; // p1 has 48 bytes per line. make this one variable in future.
var binarizationInterval = 420; // Between 0 and 768.
// editor settings
var simplemde = new SimpleMDE({
element: document.getElementById("editorarea"),
spellChecker: false,
previewRender: (text) => {
let d = marked.parse(text);
return `<div class="content"> ${d} </div>`
}
});
async function connect() {
// Call browser popup to let user select device
let printer = await navigator.bluetooth.requestDevice({
acceptAllDevices: true,
optionalServices: ['49535343-fe7d-4ae5-8fa9-9fafd205e455']
});
console.log(printer);
let pserver = await printer.gatt.connect(); // BLE connect
btservice = await pserver.getPrimaryService('49535343-fe7d-4ae5-8fa9-9fafd205e455');
sockchar = await btservice.getCharacteristic('49535343-6daa-4d02-abf6-19569aca69fe');
notify = await btservice.getCharacteristic('49535343-1e4d-4bd9-ba61-23c647249616');
notify.startNotifications().then(() => {
notify.addEventListener('characteristicvaluechanged', (event) => {
let value = event.target.value;
// Convert raw data bytes to hex values just for the sake of showing something.
// In the "real" world, you'd use data.getUint8, data.getUint16 or even
// TextDecoder to process raw data bytes.
let arr = new Array();
for(i=0; i<value.byteLength; i++){
arr.push(value.getUint8(i));
}
let payload = arr.slice(5, -5);
console.log('Command:' , arr[1], 'Payload:', payload);
if(payload.length < 11){
console.log(arr);
} else {
let decoded = '';
for(each in payload.slice(0, -11)){
decoded += String.fromCharCode(payload[each]);
}
console.log('Ascii:', decoded);
}
})
})
}
async function selfdiag() {
await sockchar.writeValue(genpack(27));
}
async function sendprint(data) {
if (data.length < 500) {
await sockchar.writeValue(genpack(0, data));
return;
}
function aslice(arr, size) {
let ret = [];
for (let i = 0; i < arr.length; i += size) {
let piece = arr.slice(i, i + size);
ret.push(piece);
}
return ret;
}
let maxbyte = (Math.floor(500/widthbyte)) * widthbyte;
let packs = aslice(data, maxbyte);
console.log(packs)
for (each in packs) {
let m = await sockchar.writeValue(genpack(0, packs[each]));
console.log(m)
}
}
// --- JSDoc Enabled funcs
/**
*
* @param {int} cmd Command Byte (1 byte)
* @param {array} data Data Array (Max 2016 bytes)
* @param {int} packetid Packet id (1 byte)
*/
function genpack(cmd, data = [0], packetid = 0) {
function b32split(i) {
// js sucks to be a low level byte manipulator.
let r = new ArrayBuffer(4);
let v = new DataView(r);
v.setUint32(0, i, true);
let t8 = new Uint8Array(r);
let arr = [...t8];
return arr;
}
let length = data.length;
if (length > 2016) { console.error("genpack: Requested pack too large"); return null; };
let bytes = Array();
bytes.push(2); //First byte 0x02
bytes.push(cmd); // 2nd byte is command
bytes.push(packetid); // 3rd byte is packet id
// Spliting the length byte
let lengthByte = b32split(length);
bytes.push(lengthByte[0], lengthByte[1]); // 4th and 5th byte is length
// append payload, starts from 6th byte.
bytes = bytes.concat(data);
// calculate CRC32.
let crcval = CRC32.buf(data, 0x35769521);
bytes = bytes.concat(b32split(crcval)); // append that 4 bytes.
bytes.push(3); // last ending byte
let bytestream = Uint8Array.from(bytes)
return bytestream;
}
/*
* Graphical rendering
*/
async function textRender(elementid){
let out = document.getElementById(elementid);
out.innerHTML = marked.parse(simplemde.value());
await bitmapRender(elementid);
out.innerHTML = '';
/*
let node = document.createElement('div');
node.innerHTML = marked.parse(simplemde.value());
await bitmapRender(node);*/
}
async function bitmapRender(elementid){
let node = document.getElementById(elementid);
// canvas renderer: bindata is the bytearray.
let bindata; // this is goint to be the binary bytearray.
// in future swapping to another renderer is just rewrite this part.
// width is always (widthbyte * 8) bytes.
let canvas = await html2canvas(node, {
width: widthbyte * 4,
windowWidth: widthbyte * 4,
onclone: (cloned) => {
cloned.getElementById(elementid).style.display = 'block'
}
});
console.log(canvas);
bindata = canvas.getContext('2d').getImageData(0,0,canvas.width, canvas.height).data;
//document.body.appendChild(canvas);
// canvas render done, rest is good.
console.log(bindata);
// Get image binarized
let binarized = new Array();
for(let i=0; i<bindata.length;i+=4){
let curr = bindata[i] + bindata[i+1] + bindata[i+2];
if(curr < binarizationInterval){
curr = 0;
} else {
curr = 1;
}
binarized.push(curr);
}
console.log(binarized);
// Encode to bit by bit
let encoded = new Array();
for (let i=0; i<binarized.length; i+=8){
let t = 0;
for(let j=0; j<8; j++){
let n = binarized[i+j];
if(n == 1){ // now 1 is white 0 is black
t = t * 2;
} else {
t = t * 2 + 1;
}
}
encoded.push(t)
}
console.log(encoded);
// send to print
await sendprint(encoded);
await sockchar.writeValue(genpack(26,[210]));
}