Initial implementation of adding and removing listeners and emitting an event
This commit is contained in:
		| @@ -110,14 +110,16 @@ RETURN_SYSTEM: | ||||
|   return es; | ||||
| } | ||||
|  | ||||
| void es_deinit(EventSystem event_system) { | ||||
|   if (IS_INVALID_SYSTEM(event_system)) { | ||||
| void es_deinit(EventSystem *event_system) { | ||||
|   if (!event_system || IS_INVALID_SYSTEM((*event_system))) { | ||||
|     return; | ||||
|   } | ||||
|  | ||||
|   ESInternal *es = get_event_system_internal(event_system); | ||||
|   ESInternal *es = get_event_system_internal(*event_system); | ||||
|  | ||||
|   munmap(system, es->alloc_size); | ||||
|  | ||||
|   event_system->id = 0; | ||||
| } | ||||
|  | ||||
| Event es_register_event(EventSystem event_system) { | ||||
| @@ -174,11 +176,88 @@ void es_deregister_event(EventSystem event_system, Event event) { | ||||
|   } | ||||
| } | ||||
|  | ||||
| EventListener es_add_event_listener(EventSystem event_system, Event event, EventCallback *listener) {} | ||||
| EventListener es_add_event_listener(EventSystem event_system, Event event, EventCallback callback) { | ||||
|   EventListener listener = INVALID_LISTENER; | ||||
|  | ||||
| void es_remove_event_listener(EventSystem event_system, EventListener listener) {} | ||||
|   if (IS_INVALID_SYSTEM(event_system) || IS_INVALID_EVENT(event) || !callback) { | ||||
|     goto RETURN_LISTENER; | ||||
|   } | ||||
|  | ||||
| void es_emit_event(EventSystem event_system, Event event, void *data) {} | ||||
|   ESInternal *es    = get_event_system_internal(event_system); | ||||
|   EventInternal *ev = get_event(es, event); | ||||
|  | ||||
|   if (ev->free_count > 0) { | ||||
|     u64 id = ev->free[--(ev->free_count)]; | ||||
|  | ||||
|     ev->free[ev->free_count] = 0; | ||||
|     ev->callbacks[id]        = callback; | ||||
|  | ||||
|     listener.id    = id; | ||||
|     listener.event = event; | ||||
|  | ||||
|     goto RETURN_LISTENER; | ||||
|   } | ||||
|  | ||||
|   if (ev->count >= ev->capacity) { | ||||
|     // TODO (Abdelrahman): Handle reallocating when out of callbacks | ||||
|     goto RETURN_LISTENER; | ||||
|   } | ||||
|  | ||||
|   u64 id = ++(ev->count); | ||||
|  | ||||
|   ev->callbacks[id] = callback; | ||||
|  | ||||
|   listener.id    = id; | ||||
|   listener.event = event; | ||||
|  | ||||
| RETURN_LISTENER: | ||||
|   return listener; | ||||
| } | ||||
|  | ||||
| void es_remove_event_listener(EventSystem event_system, EventListener listener) { | ||||
|   if (IS_INVALID_SYSTEM(event_system) || IS_INVALID_LISTENER(listener)) { | ||||
|     return; | ||||
|   } | ||||
|  | ||||
|   ESInternal *es    = get_event_system_internal(event_system); | ||||
|   EventInternal *ev = get_event(es, listener.event); | ||||
|  | ||||
|   if (listener.id > ev->count) { | ||||
|     return; | ||||
|   } | ||||
|  | ||||
|   if (ev->callbacks[listener.id] == NULL) { | ||||
|     return; | ||||
|   } | ||||
|  | ||||
|   ev->callbacks[listener.id]   = NULL; | ||||
|   ev->free[(ev->free_count)++] = listener.id;  | ||||
|  | ||||
|   if (listener.id == ev->count) { | ||||
|     ev->count -= 1; | ||||
|   } | ||||
| } | ||||
|  | ||||
| void es_emit_event(EventSystem event_system, Event event, void *data) { | ||||
|   if (IS_INVALID_SYSTEM(event_system) || IS_INVALID_EVENT(event)) { | ||||
|     return; | ||||
|   } | ||||
|  | ||||
|   ESInternal *es = get_event_system_internal(event_system); | ||||
|   if (event.id > es->event_count) { | ||||
|     return; | ||||
|   } | ||||
|  | ||||
|   EventInternal *ev = get_event(es, event); | ||||
|   EventCallback callback; | ||||
|   for (int i = 0; i < ev->count; ++i) { | ||||
|     callback = ev->callbacks[i + 1]; | ||||
|     if (!callback) { | ||||
|       continue; | ||||
|     } | ||||
|     callback(data); | ||||
|   } | ||||
| } | ||||
|  | ||||
| // INTERNAL | ||||
|  | ||||
|   | ||||
| @@ -25,12 +25,12 @@ struct event_listener { | ||||
|   u64 id; | ||||
| }; | ||||
|  | ||||
| typedef void (EventCallback)(void *data); | ||||
| typedef void (*EventCallback)(void *data); | ||||
|  | ||||
| EventSystem   es_init(u64 initial_event_capacity, u64 initial_listeners_capacity); | ||||
| void          es_deinit(EventSystem event_system); | ||||
| void          es_deinit(EventSystem *event_system); | ||||
| Event         es_register_event(EventSystem event_system); | ||||
| void          es_deregister_event(EventSystem event_system, Event event); | ||||
| EventListener es_add_event_listener(EventSystem event_system, Event event, EventCallback *listener); | ||||
| EventListener es_add_event_listener(EventSystem event_system, Event event, EventCallback callback); | ||||
| void          es_remove_event_listener(EventSystem event_system, EventListener listener); | ||||
| void          es_emit_event(EventSystem event_system, Event event, void *data); | ||||
|   | ||||
							
								
								
									
										76
									
								
								src/main.c
									
									
									
									
									
								
							
							
						
						
									
										76
									
								
								src/main.c
									
									
									
									
									
								
							| @@ -1,6 +1,15 @@ | ||||
| #include "event_system.h" | ||||
| #include <stdio.h> | ||||
|  | ||||
| #define ARR_LEN(ARR) (sizeof(ARR) / sizeof(ARR[0])) | ||||
|  | ||||
| void callback(void *data); | ||||
| void callback1(void *data); | ||||
| void callback2(void *data); | ||||
| void callback3(void *data); | ||||
| void callback4(void *data); | ||||
| void callback5(void *data); | ||||
|  | ||||
| int main(void) { | ||||
|   EventSystem es = es_init(16, 64); | ||||
|  | ||||
| @@ -22,7 +31,72 @@ int main(void) { | ||||
|     printf("%lu\n", ev.id); | ||||
|   } | ||||
|  | ||||
|   es_deinit(es); | ||||
|   printf("\n"); | ||||
|  | ||||
|   es_deregister_event(es, (Event){ .id = 10 }); | ||||
|   Event ev = es_register_event(es); | ||||
|   for (int i = 0; i < 10; ++i) { | ||||
|     EventListener listener = es_add_event_listener(es, ev, callback); | ||||
|     printf("Event: %lu, ID: %lu\n", listener.event.id, listener.id); | ||||
|   } | ||||
|  | ||||
|   printf("\n"); | ||||
|  | ||||
|   for (int i = 5; i < 8; ++i) { | ||||
|     es_remove_event_listener(es, (EventListener){ .event = ev, .id = i }); | ||||
|   } | ||||
|  | ||||
|   for (int i = 0; i < 3; ++i) { | ||||
|     EventListener listener = es_add_event_listener(es, ev, callback); | ||||
|     printf("Event: %lu, ID: %lu\n", listener.event.id, listener.id); | ||||
|   } | ||||
|  | ||||
|   printf("\n"); | ||||
|  | ||||
|   EventCallback callbacks[] = {callback1, callback2, callback3, callback4, callback5}; | ||||
|   EventListener listeners[ARR_LEN(callbacks)] = {0}; | ||||
|   Event ev_with_callbacks = (Event){ .id = 20 }; | ||||
|   for (int i = 0; i < ARR_LEN(callbacks); ++i) { | ||||
|     listeners[i] = es_add_event_listener(es, ev_with_callbacks, callbacks[i]); | ||||
|   } | ||||
|  | ||||
|   es_emit_event(es, ev_with_callbacks, (void *)0); | ||||
|  | ||||
|   printf("\n"); | ||||
|  | ||||
|   es_remove_event_listener(es, listeners[2]); | ||||
|  | ||||
|   es_emit_event(es, ev_with_callbacks, (void *)0); | ||||
|  | ||||
|   printf("\n"); | ||||
|  | ||||
|   printf("SYSTEM: %lu\n", es.id); | ||||
|   es_deinit(&es); | ||||
|   printf("SYSTEM: %lu\n", es.id); | ||||
|  | ||||
|   return 0; | ||||
| } | ||||
|  | ||||
| void callback(void *data) { | ||||
|   return; | ||||
| } | ||||
|  | ||||
| void callback1(void *data) { | ||||
|   printf("Hello from callback1\n"); | ||||
| } | ||||
|  | ||||
| void callback2(void *data) { | ||||
|   printf("Hello from callback2\n"); | ||||
| } | ||||
|  | ||||
| void callback3(void *data) { | ||||
|   printf("Hello from callback3\n"); | ||||
| } | ||||
|  | ||||
| void callback4(void *data) { | ||||
|   printf("Hello from callback4\n"); | ||||
| } | ||||
|  | ||||
| void callback5(void *data) { | ||||
|   printf("Hello from callback5\n"); | ||||
| } | ||||
|   | ||||
		Reference in New Issue
	
	Block a user