219 lines
6.4 KiB
TypeScript
219 lines
6.4 KiB
TypeScript
// Handle serialization of the event data across the IPC boundarytype SerialziedEvent = {};
|
|
|
|
import { retriveSelectValue, retriveValues } from "./form";
|
|
|
|
export type AppTouchEvent = TouchEvent;
|
|
|
|
export type SerializedEvent = {
|
|
values?: { [key: string]: FormDataEntryValue[] };
|
|
value?: string;
|
|
[key: string]: any;
|
|
};
|
|
|
|
export function serializeEvent(event: Event, target: EventTarget): SerializedEvent {
|
|
let contents = {};
|
|
|
|
// merge the object into the contents
|
|
let extend = (obj: any) => (contents = { ...contents, ...obj });
|
|
|
|
if (event instanceof WheelEvent) { extend(serializeWheelEvent(event)) };
|
|
if (event instanceof MouseEvent) { extend(serializeMouseEvent(event)) }
|
|
if (event instanceof KeyboardEvent) { extend(serializeKeyboardEvent(event)) }
|
|
|
|
if (event instanceof InputEvent) { extend(serializeInputEvent(event, target)) }
|
|
if (event instanceof PointerEvent) { extend(serializePointerEvent(event)) }
|
|
if (event instanceof AnimationEvent) { extend(serializeAnimationEvent(event)) }
|
|
if (event instanceof TransitionEvent) { extend({ property_name: event.propertyName, elapsed_time: event.elapsedTime, pseudo_element: event.pseudoElement, }) }
|
|
if (event instanceof CompositionEvent) { extend({ data: event.data, }) }
|
|
if (event instanceof DragEvent) { extend(serializeDragEvent(event)) }
|
|
if (event instanceof FocusEvent) { extend({}) }
|
|
if (event instanceof ClipboardEvent) { extend({}) }
|
|
|
|
// safari is quirky and doesn't have TouchEvent
|
|
if (typeof TouchEvent !== 'undefined' && event instanceof TouchEvent) { extend(serializeTouchEvent(event)); }
|
|
|
|
if (event.type === "submit" || event.type === "reset" || event.type === "click" || event.type === "change" || event.type === "input") {
|
|
extend(serializeInputEvent(event as InputEvent, target));
|
|
}
|
|
|
|
// If there's any files, we need to serialize them
|
|
if (event instanceof DragEvent) {
|
|
// let files: { [key: string]: Uint8Array } = {};
|
|
// if (event.dataTransfer && event.dataTransfer.files) {
|
|
// files["a"] = new Uint8Array(0);
|
|
// // files = {
|
|
// // entries: Array.from(event.dataTransfer.files).map((file) => {
|
|
// // return {
|
|
// // name: file.name,
|
|
// // type: file.type,
|
|
// // size: file.size,
|
|
// // last_modified: file.lastModified,
|
|
// // };
|
|
// // }
|
|
// // };
|
|
// // files = await serializeFileList(event.dataTransfer.files);
|
|
// }
|
|
// extend({ files: files });
|
|
}
|
|
|
|
return contents;
|
|
}
|
|
|
|
function serializeInputEvent(event: InputEvent, target: EventTarget): SerializedEvent {
|
|
let contents: SerializedEvent = {};
|
|
|
|
// Attempt to retrieve the values from the form
|
|
if (target instanceof HTMLElement) {
|
|
let values = retriveValues(event, target);
|
|
contents.values = values.values;
|
|
contents.valid = values.valid;
|
|
}
|
|
|
|
if (event.target instanceof HTMLInputElement) {
|
|
let target = event.target;
|
|
let value = target.value ?? target.textContent ?? "";
|
|
|
|
if (target.type === "checkbox") {
|
|
value = target.checked ? "true" : "false";
|
|
} else if (target.type === "radio") {
|
|
value = target.value;
|
|
}
|
|
|
|
contents.value = value;
|
|
}
|
|
|
|
if (event.target instanceof HTMLTextAreaElement) {
|
|
contents.value = event.target.value;
|
|
}
|
|
|
|
if (event.target instanceof HTMLSelectElement) {
|
|
contents.value = retriveSelectValue(event.target).join(",");
|
|
}
|
|
|
|
// Ensure the serializer isn't quirky
|
|
if (contents.value === undefined) {
|
|
contents.value = "";
|
|
}
|
|
|
|
|
|
return contents;
|
|
}
|
|
|
|
|
|
|
|
function serializeWheelEvent(event: WheelEvent): SerializedEvent {
|
|
return {
|
|
delta_x: event.deltaX,
|
|
delta_y: event.deltaY,
|
|
delta_z: event.deltaZ,
|
|
delta_mode: event.deltaMode,
|
|
};
|
|
}
|
|
|
|
function serializeTouchEvent(event: TouchEvent): SerializedEvent {
|
|
return {
|
|
alt_key: event.altKey,
|
|
ctrl_key: event.ctrlKey,
|
|
meta_key: event.metaKey,
|
|
shift_key: event.shiftKey,
|
|
changed_touches: event.changedTouches,
|
|
target_touches: event.targetTouches,
|
|
touches: event.touches,
|
|
};
|
|
}
|
|
|
|
function serializePointerEvent(event: PointerEvent): SerializedEvent {
|
|
return {
|
|
alt_key: event.altKey,
|
|
button: event.button,
|
|
buttons: event.buttons,
|
|
client_x: event.clientX,
|
|
client_y: event.clientY,
|
|
ctrl_key: event.ctrlKey,
|
|
meta_key: event.metaKey,
|
|
page_x: event.pageX,
|
|
page_y: event.pageY,
|
|
screen_x: event.screenX,
|
|
screen_y: event.screenY,
|
|
shift_key: event.shiftKey,
|
|
pointer_id: event.pointerId,
|
|
width: event.width,
|
|
height: event.height,
|
|
pressure: event.pressure,
|
|
tangential_pressure: event.tangentialPressure,
|
|
tilt_x: event.tiltX,
|
|
tilt_y: event.tiltY,
|
|
twist: event.twist,
|
|
pointer_type: event.pointerType,
|
|
is_primary: event.isPrimary,
|
|
};
|
|
}
|
|
|
|
function serializeMouseEvent(event: MouseEvent): SerializedEvent {
|
|
return {
|
|
alt_key: event.altKey,
|
|
button: event.button,
|
|
buttons: event.buttons,
|
|
client_x: event.clientX,
|
|
client_y: event.clientY,
|
|
ctrl_key: event.ctrlKey,
|
|
meta_key: event.metaKey,
|
|
offset_x: event.offsetX,
|
|
offset_y: event.offsetY,
|
|
page_x: event.pageX,
|
|
page_y: event.pageY,
|
|
screen_x: event.screenX,
|
|
screen_y: event.screenY,
|
|
shift_key: event.shiftKey,
|
|
};
|
|
}
|
|
|
|
function serializeKeyboardEvent(event: KeyboardEvent): SerializedEvent {
|
|
return {
|
|
char_code: event.charCode,
|
|
is_composing: event.isComposing,
|
|
key: event.key,
|
|
alt_key: event.altKey,
|
|
ctrl_key: event.ctrlKey,
|
|
meta_key: event.metaKey,
|
|
key_code: event.keyCode,
|
|
shift_key: event.shiftKey,
|
|
location: event.location,
|
|
repeat: event.repeat,
|
|
which: event.which,
|
|
code: event.code,
|
|
};
|
|
}
|
|
|
|
function serializeAnimationEvent(event: AnimationEvent): SerializedEvent {
|
|
return {
|
|
animation_name: event.animationName,
|
|
elapsed_time: event.elapsedTime,
|
|
pseudo_element: event.pseudoElement,
|
|
};
|
|
}
|
|
|
|
function serializeDragEvent(event: DragEvent): SerializedEvent {
|
|
let files = undefined;
|
|
// On desktop if there is file data, we insert it from wry. We just add a placeholder to let the rust side of dioxus know there's files
|
|
if (
|
|
event.dataTransfer &&
|
|
event.dataTransfer.files &&
|
|
event.dataTransfer.files.length > 0
|
|
) {
|
|
files = {
|
|
files: { placeholder: [] },
|
|
};
|
|
}
|
|
return {
|
|
mouse: {
|
|
alt_key: event.altKey,
|
|
ctrl_key: event.ctrlKey,
|
|
meta_key: event.metaKey,
|
|
shift_key: event.shiftKey,
|
|
...serializeMouseEvent(event),
|
|
},
|
|
files,
|
|
};
|
|
}
|