2
0
Эх сурвалжийг харах

Removed event queue from add_*_event_listener JS functions and added event hook callback

p2jason 9 сар өмнө
parent
commit
e825326d73

+ 9 - 10
core/sys/wasm/js/events.odin

@@ -313,14 +313,14 @@ foreign dom_lib {
 	dispatch_custom_event            :: proc(id: string, name: string, options := Event_Options{}) -> bool ---
 }
 
-add_event_listener :: proc(id: string, kind: Event_Kind, user_data: rawptr, callback: proc(e: Event), flags := Listener_Flags{}) -> bool {
+add_event_listener :: proc(id: string, kind: Event_Kind, user_data: rawptr, callback: proc(e: Event), use_capture := false) -> bool {
 	@(default_calling_convention="contextless")
 	foreign dom_lib {
 		@(link_name="add_event_listener")
-		_add_event_listener :: proc(id: string, name: string, name_code: Event_Kind, user_data: rawptr, callback: proc "odin" (Event), use_capture: bool, prevent_default: bool, stop_prop: bool, stop_imm_prop: bool) -> bool ---
+		_add_event_listener :: proc(id: string, name: string, name_code: Event_Kind, user_data: rawptr, callback: proc "odin" (Event), use_capture: bool) -> bool ---
 	}
 	// TODO: Pointer_Lock_Change etc related stuff for all different browsers
-	return _add_event_listener(id, event_kind_string[kind], kind, user_data, callback, .Use_Capture in flags, .Prevent_Default in flags, .Stop_Propagation in flags, .Stop_Immediate_Propagation in flags)
+	return _add_event_listener(id, event_kind_string[kind], kind, user_data, callback, use_capture)
 }
 
 remove_event_listener :: proc(id: string, kind: Event_Kind, user_data: rawptr, callback: proc(e: Event)) -> bool {
@@ -332,13 +332,13 @@ remove_event_listener :: proc(id: string, kind: Event_Kind, user_data: rawptr, c
 	return _remove_event_listener(id, event_kind_string[kind], user_data, callback)
 }
 
-add_window_event_listener :: proc(kind: Event_Kind, user_data: rawptr, callback: proc(e: Event), flags := Listener_Flags{}) -> bool {
+add_window_event_listener :: proc(kind: Event_Kind, user_data: rawptr, callback: proc(e: Event), use_capture := false) -> bool {
 	@(default_calling_convention="contextless")
 	foreign dom_lib {
 		@(link_name="add_window_event_listener")
-		_add_window_event_listener :: proc(name: string, name_code: Event_Kind, user_data: rawptr, callback: proc "odin" (Event), use_capture: bool, prevent_default: bool, stop_prop: bool, stop_imm_prop: bool) -> bool ---
+		_add_window_event_listener :: proc(name: string, name_code: Event_Kind, user_data: rawptr, callback: proc "odin" (Event), use_capture: bool) -> bool ---
 	}
-	return _add_window_event_listener(event_kind_string[kind], kind, user_data, callback, .Use_Capture in flags, .Prevent_Default in flags, .Stop_Propagation in flags, .Stop_Immediate_Propagation in flags)
+	return _add_window_event_listener(event_kind_string[kind], kind, user_data, callback, use_capture)
 }
 
 remove_window_event_listener :: proc(kind: Event_Kind, user_data: rawptr, callback: proc(e: Event)) -> bool {
@@ -357,15 +357,14 @@ remove_event_listener_from_event :: proc(e: Event) -> bool {
 	return remove_event_listener(e.id, e.kind, e.user_data, e.callback)
 }
 
-add_custom_event_listener :: proc(id: string, name: string, user_data: rawptr, callback: proc(e: Event), flags := Listener_Flags{}) -> bool {
+add_custom_event_listener :: proc(id: string, name: string, user_data: rawptr, callback: proc(e: Event), use_capture := false) -> bool {
 	@(default_calling_convention="contextless")
 	foreign dom_lib {
 		@(link_name="add_event_listener")
-		_add_event_listener :: proc(id: string, name: string, name_code: Event_Kind, user_data: rawptr, callback: proc "odin" (Event), use_capture: bool, prevent_default: bool, stop_prop: bool, stop_imm_prop: bool) -> bool ---
+		_add_event_listener :: proc(id: string, name: string, name_code: Event_Kind, user_data: rawptr, callback: proc "odin" (Event), use_capture: bool) -> bool ---
 	}
-	return _add_event_listener(id, name, .Custom, user_data, callback, .Use_Capture in flags, .Prevent_Default in flags, .Stop_Propagation in flags, .Stop_Immediate_Propagation in flags)
+	return _add_event_listener(id, name, .Custom, user_data, callback, use_capture)
 }
-
 remove_custom_event_listener :: proc(id: string, name: string, user_data: rawptr, callback: proc(e: Event)) -> bool {
 	@(default_calling_convention="contextless")
 	foreign dom_lib {

+ 34 - 25
core/sys/wasm/js/odin.js

@@ -1259,13 +1259,30 @@ class WebGLInterface {
 };
 
 
-function odinSetupDefaultImports(wasmMemoryInterface, consoleElement, memory, eventQueue, event_temp) {
+function odinSetupDefaultImports(wasmMemoryInterface, consoleElement, memory, eventHookCallback) {
 	const MAX_INFO_CONSOLE_LINES = 512;
 	let infoConsoleLines = new Array();
 	let currentLine = {};
 	currentLine[false] = "";
 	currentLine[true] = "";
 	let prevIsError = false;
+	
+	let event_temp = {};
+
+	const onEventReceived = (event_data, data, callback) => {
+		event_temp.data = event_data;
+		
+		const exports = wasmMemoryInterface.exports;
+		const odin_ctx = exports.default_context_ptr();
+		
+		const mute = eventHookCallback && !eventHookCallback(event_data.event, data, callback);
+	
+		if (!mute) {
+			exports.odin_dom_do_event_callback(data, callback, odin_ctx);
+		}
+		
+		event_temp.data = null;
+	};
 
 	const writeToConsole = (line, isError) => {
 		if (!line) {
@@ -1579,7 +1596,7 @@ function odinSetupDefaultImports(wasmMemoryInterface, consoleElement, memory, ev
 				}
 			},
 
-			add_event_listener: (id_ptr, id_len, name_ptr, name_len, name_code, data, callback, use_capture, prevent_default, stop_prop, stop_imm_prop) => {
+			add_event_listener: (id_ptr, id_len, name_ptr, name_len, name_code, data, callback, use_capture) => {
 				let id = wasmMemoryInterface.loadString(id_ptr, id_len);
 				let name = wasmMemoryInterface.loadString(name_ptr, name_len);
 				let element = getElement(id);
@@ -1594,18 +1611,14 @@ function odinSetupDefaultImports(wasmMemoryInterface, consoleElement, memory, ev
 					event_data.event = e;
 					event_data.name_code = name_code;
 
-					if (prevent_default) e.preventDefault();
-					if (stop_prop) e.stopPropagation();
-					if (stop_imm_prop) e.stopImmediatePropagation();
-
-					eventQueue.push({event_data: event_data, data: data, callback: callback});
+					onEventReceived(event_data, data, callback);
 				};
 				wasmMemoryInterface.listenerMap[{data: data, callback: callback}] = listener;
 				element.addEventListener(name, listener, !!use_capture);
 				return true;
 			},
 
-			add_window_event_listener: (name_ptr, name_len, name_code, data, callback, use_capture, prevent_default, stop_prop, stop_imm_prop) => {
+			add_window_event_listener: (name_ptr, name_len, name_code, data, callback, use_capture) => {
 				let name = wasmMemoryInterface.loadString(name_ptr, name_len);
 				let element = window;
 				let listener = (e) => {
@@ -1615,11 +1628,7 @@ function odinSetupDefaultImports(wasmMemoryInterface, consoleElement, memory, ev
 					event_data.event = e;
 					event_data.name_code = name_code;
 
-					if (prevent_default) e.preventDefault();
-					if (stop_prop) e.stopPropagation();
-					if (stop_imm_prop) e.stopImmediatePropagation();
-
-					eventQueue.push({event_data: event_data, data: data, callback: callback});
+					onEventReceived(event_data, data, callback);
 				};
 				wasmMemoryInterface.listenerMap[{data: data, callback: callback}] = listener;
 				element.addEventListener(name, listener, !!use_capture);
@@ -1900,23 +1909,30 @@ function odinSetupDefaultImports(wasmMemoryInterface, consoleElement, memory, ev
 	};
 };
 
+/**
+ * A callback used to intersept events that are being dispatched to the application.
+ * @callback EventHookCallback
+ * @param {Object} [event] - The event that is about to be sent to the application.
+ * @param {Object} [data] - The user data that was passed in when the event listener for {@param event} was registered.
+ * @param {Object} [callback] - The callback that was passed in when the event listener for {@param event} was registered.
+ * @return {bool} If false, the event will not be sent to the application.
+ */
+
 /**
  * @param {string} wasmPath                          - Path to the WASM module to run
  * @param {?HTMLPreElement} consoleElement           - Optional console/pre element to append output to, in addition to the console
  * @param {any} extraForeignImports                  - Imports, in addition to the default runtime to provide the module
  * @param {?WasmMemoryInterface} wasmMemoryInterface - Optional memory to use instead of the defaults
  * @param {?int} intSize                             - Size (in bytes) of the integer type, should be 4 on `js_wasm32` and 8 on `js_wasm64p32`
+ * @param {?EventHookCallback} eventHookCallback     - Callback that will be invoked when an event is dispatched to the application
  */
-async function runWasm(wasmPath, consoleElement, extraForeignImports, wasmMemoryInterface, intSize = 4) {
+async function runWasm(wasmPath, consoleElement, extraForeignImports, wasmMemoryInterface, intSize = 4, eventHookCallback = null) {
 	if (!wasmMemoryInterface) {
 		wasmMemoryInterface = new WasmMemoryInterface();
 	}
 	wasmMemoryInterface.setIntSize(intSize);
 
-	let eventQueue = new Array();
-	let event_temp = {};
-
-	let imports = odinSetupDefaultImports(wasmMemoryInterface, consoleElement, wasmMemoryInterface.memory, eventQueue, event_temp);
+	let imports = odinSetupDefaultImports(wasmMemoryInterface, consoleElement, wasmMemoryInterface.memory, eventHookCallback);
 	let exports = {};
 
 	if (extraForeignImports !== undefined) {
@@ -1956,13 +1972,6 @@ async function runWasm(wasmPath, consoleElement, extraForeignImports, wasmMemory
 			const dt = (currTimeStamp - prevTimeStamp)*0.001;
 			prevTimeStamp = currTimeStamp;
 
-			while (eventQueue.length > 0) {
-				let e = eventQueue.shift()
-				event_temp.data = e.event_data;
-				exports.odin_dom_do_event_callback(e.data, e.callback, odin_ctx);
-			}
-			event_temp.data = null;
-
 			if (!exports.step(dt, odin_ctx)) {
 				exports._end();
 				return;