csharpc-sharpdotnetxamlavaloniauicross-platformcross-platform-xamlavaloniaguimulti-platformuser-interfacedotnetcore
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
84 lines
2.5 KiB
84 lines
2.5 KiB
import { InputEventMessageBase } from "src/Models/Input/InputEventMessageBase";
|
|
|
|
export interface PreviewerFrame {
|
|
data: ImageData;
|
|
dpiX: number;
|
|
dpiY: number;
|
|
}
|
|
|
|
export class PreviewerServerConnection {
|
|
private nextFrame = {
|
|
width: 0,
|
|
height: 0,
|
|
stride: 0,
|
|
dpiX: 0,
|
|
dpiY: 0,
|
|
sequenceId: "0"
|
|
};
|
|
|
|
public currentFrame: PreviewerFrame | null;
|
|
private handlers = new Set<(frame: PreviewerFrame | null) => void>();
|
|
private conn: WebSocket;
|
|
|
|
public addFrameListener(listener: (frame: PreviewerFrame | null) => void) {
|
|
this.handlers.add(listener);
|
|
if (this.currentFrame)
|
|
listener(this.currentFrame);
|
|
}
|
|
|
|
public removeFrameListener(listener: (frame: PreviewerFrame | null) => void) {
|
|
this.handlers.delete(listener);
|
|
}
|
|
|
|
public sendMouseEvent(message: InputEventMessageBase) {
|
|
this.conn.send(message.toString());
|
|
}
|
|
|
|
constructor(uri: string) {
|
|
this.currentFrame = null;
|
|
var conn = this.conn = new WebSocket(uri);
|
|
conn.binaryType = 'arraybuffer';
|
|
|
|
const onMessage = this.onMessage;
|
|
conn.onmessage = msg => onMessage(msg);
|
|
|
|
const onClose = () => this.setFrame(null);
|
|
conn.onclose = () => onClose();
|
|
conn.onerror = (err: Event) => {
|
|
onClose();
|
|
console.log("Connection error: " + err);
|
|
}
|
|
}
|
|
|
|
private onMessage = (msg: MessageEvent) => {
|
|
if (typeof msg.data == 'string' || msg.data instanceof String) {
|
|
const parts = msg.data.split(':');
|
|
if (parts[0] == 'frame') {
|
|
this.nextFrame = {
|
|
sequenceId: parts[1],
|
|
width: parseInt(parts[2]),
|
|
height: parseInt(parts[3]),
|
|
stride: parseInt(parts[4]),
|
|
dpiX: parseInt(parts[5]),
|
|
dpiY: parseInt(parts[6])
|
|
}
|
|
}
|
|
} else if (msg.data instanceof ArrayBuffer) {
|
|
const arr = new Uint8ClampedArray(msg.data, 0);
|
|
const imageData = new ImageData(arr, this.nextFrame.width, this.nextFrame.height);
|
|
this.conn.send('frame-received:' + this.nextFrame.sequenceId);
|
|
this.setFrame({
|
|
data: imageData,
|
|
dpiX: this.nextFrame.dpiX,
|
|
dpiY: this.nextFrame.dpiY
|
|
});
|
|
|
|
|
|
}
|
|
};
|
|
|
|
private setFrame(frame: PreviewerFrame | null) {
|
|
this.currentFrame = frame;
|
|
this.handlers.forEach(h => h(this.currentFrame));
|
|
}
|
|
}
|
|
|