ecore_cocoa: release resources on window close event

@fix this patch:

catch the window close event from cocoa and send an ecore event
this event is catched by a handler in ecore_evas wich will
call the registered fn_delete_request (from elementary for instance)

/!\ this patch is currently incomplete and leads to a segv when
closing the last window

Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
This commit is contained in:
pierre lamot 2015-01-30 17:15:55 +01:00 committed by Cedric BAIL
parent 358bd3eb25
commit 6ea9b476ad
5 changed files with 45 additions and 4 deletions

View File

@ -38,6 +38,7 @@ EAPI extern int ECORE_COCOA_EVENT_GOT_FOCUS;
EAPI extern int ECORE_COCOA_EVENT_LOST_FOCUS;
EAPI extern int ECORE_COCOA_EVENT_RESIZE;
EAPI extern int ECORE_COCOA_EVENT_EXPOSE;
EAPI extern int ECORE_COCOA_EVENT_WINDOW_DESTROY;
typedef void * Ecore_Cocoa_Window_Id;
typedef struct _Ecore_Cocoa_Event_Video_Resize Ecore_Cocoa_Event_Video_Resize;

View File

@ -20,6 +20,7 @@ EAPI int ECORE_COCOA_EVENT_GOT_FOCUS = 0;
EAPI int ECORE_COCOA_EVENT_LOST_FOCUS = 0;
EAPI int ECORE_COCOA_EVENT_RESIZE = 0;
EAPI int ECORE_COCOA_EVENT_EXPOSE = 0;
EAPI int ECORE_COCOA_EVENT_WINDOW_DESTROY = 0;
static int _ecore_cocoa_init_count = 0;
@ -50,6 +51,7 @@ ecore_cocoa_init(void)
ECORE_COCOA_EVENT_LOST_FOCUS = ecore_event_type_new();
ECORE_COCOA_EVENT_RESIZE = ecore_event_type_new();
ECORE_COCOA_EVENT_EXPOSE = ecore_event_type_new();
ECORE_COCOA_EVENT_WINDOW_DESTROY = ecore_event_type_new();
/* Init the Application handler */
[Ecore_Cocoa_Application sharedApplication];

View File

@ -50,6 +50,17 @@
- (void)windowWillClose:(NSNotification *) EINA_UNUSED notification
{
NSLog(@"window is going to be closed");
Ecore_Cocoa_Event_Window *event;
event = malloc(sizeof(Ecore_Cocoa_Event_Window));
if (event == NULL)
{
// FIXME Use Eina_Log
printf("Failed to allocate Ecore_Cocoa_Event_Window_destroy\n");
return;
}
event->wid = [notification object];
ecore_event_add(ECORE_COCOA_EVENT_WINDOW_DESTROY, event, NULL, NULL);
}
- (void)windowDidResize:(NSNotification *) EINA_UNUSED notif

View File

@ -20,7 +20,7 @@ static int _ecore_evas_init_count = 0;
// FIXME: In case we have a lot of windows per app, we should probably use another container
// like a rbtree or a dictionnary-based container
static Eina_List *ecore_evases = NULL;
static Ecore_Event_Handler *ecore_evas_event_handlers[4] = {
static Ecore_Event_Handler *ecore_evas_event_handlers[5] = {
NULL, NULL, NULL, NULL
};
static Ecore_Idle_Enterer *ecore_evas_idle_enterer = NULL;
@ -204,6 +204,27 @@ _ecore_evas_cocoa_event_video_expose(void *data EINA_UNUSED, int type EINA_UNUSE
return ECORE_CALLBACK_PASS_ON;
}
static Eina_Bool
_ecore_evas_cocoa_event_window_destroy(void *data EINA_UNUSED, int type EINA_UNUSED, void *event)
{
Ecore_Cocoa_Event_Window *e = event;
Ecore_Evas *ee;
DBG("Window destroy");
ee = _ecore_evas_cocoa_match(e->wid);
if (!ee)
{
WRN("%s: Unregistered Ecore_Evas for window Id %p\n", __func__, e->wid);
return ECORE_CALLBACK_PASS_ON;
}
if (ee->func.fn_delete_request) ee->func.fn_delete_request(ee);
return ECORE_CALLBACK_PASS_ON;
}
//static int
//_ecore_evas_idle_enter(void *data EINA_UNUSED)
//{
@ -238,6 +259,7 @@ _ecore_evas_cocoa_init(void)
ecore_evas_event_handlers[1] = ecore_event_handler_add(ECORE_COCOA_EVENT_LOST_FOCUS, _ecore_evas_cocoa_event_lost_focus, NULL);
ecore_evas_event_handlers[2] = ecore_event_handler_add(ECORE_COCOA_EVENT_RESIZE, _ecore_evas_cocoa_event_video_resize, NULL);
ecore_evas_event_handlers[3] = ecore_event_handler_add(ECORE_COCOA_EVENT_EXPOSE, _ecore_evas_cocoa_event_video_expose, NULL);
ecore_evas_event_handlers[4] = ecore_event_handler_add(ECORE_COCOA_EVENT_WINDOW_DESTROY, _ecore_evas_cocoa_event_window_destroy, NULL);
return _ecore_evas_init_count;
}
@ -462,13 +484,20 @@ _ecore_evas_screen_geometry_get(const Ecore_Evas *ee EINA_UNUSED, int *x, int *y
printf("screen geometry_get %dx%d\n", *w, *h);
}
static void
_ecore_evas_callback_delete_request_set(Ecore_Evas *ee, Ecore_Evas_Event_Cb func)
{
ee->func.fn_delete_request = func;
}
static Ecore_Evas_Engine_Func _ecore_cocoa_engine_func =
{
_ecore_evas_cocoa_free,
NULL,
NULL,
NULL,
NULL,
_ecore_evas_callback_delete_request_set,
NULL,
NULL,
NULL,

View File

@ -78,8 +78,6 @@ eng_info_free(Evas *e EINA_UNUSED, void *info)
{
Evas_Engine_Info_GL_Cocoa *in;
DBG("Info %p", info);
eina_log_domain_unregister(_evas_engine_gl_cocoa_log_dom);
in = (Evas_Engine_Info_GL_Cocoa *)info;
free(in);
}