Index: uspace/lib/display/include/types/display.h
===================================================================
--- uspace/lib/display/include/types/display.h	(revision 4645b2c34ead210c775e6151cfd474eff304e55a)
+++ uspace/lib/display/include/types/display.h	(revision b43edabea6b4e7a51e81261a5aec4d8b514e4e8f)
@@ -39,4 +39,5 @@
 #include <fibril_synch.h>
 #include <io/kbd_event.h>
+#include <io/pos_event.h>
 #include <stdint.h>
 
@@ -58,4 +59,5 @@
 typedef struct {
 	void (*kbd_event)(void *, kbd_event_t *);
+	void (*pos_event)(void *, pos_event_t *);
 } display_wnd_cb_t;
 
Index: uspace/lib/display/include/types/display/event.h
===================================================================
--- uspace/lib/display/include/types/display/event.h	(revision 4645b2c34ead210c775e6151cfd474eff304e55a)
+++ uspace/lib/display/include/types/display/event.h	(revision b43edabea6b4e7a51e81261a5aec4d8b514e4e8f)
@@ -37,7 +37,17 @@
 
 #include <io/kbd_event.h>
+#include <io/pos_event.h>
+
+typedef enum {
+	wev_kbd,
+	wev_pos
+} display_wnd_ev_type_t;
 
 typedef struct {
-	kbd_event_t kbd_event;
+	display_wnd_ev_type_t etype;
+	union {
+		kbd_event_t kbd;
+		pos_event_t pos;
+	} ev;
 } display_wnd_ev_t;
 
Index: uspace/lib/display/src/display.c
===================================================================
--- uspace/lib/display/src/display.c	(revision 4645b2c34ead210c775e6151cfd474eff304e55a)
+++ uspace/lib/display/src/display.c	(revision b43edabea6b4e7a51e81261a5aec4d8b514e4e8f)
@@ -295,6 +295,18 @@
 			break;
 
-		if (window->cb != NULL && window->cb->kbd_event != NULL)
-			window->cb->kbd_event(window->cb_arg, &event.kbd_event);
+		switch (event.etype) {
+		case wev_kbd:
+			if (window->cb != NULL && window->cb->kbd_event != NULL) {
+				window->cb->kbd_event(window->cb_arg,
+				    &event.ev.kbd);
+			}
+			break;
+		case wev_pos:
+			if (window->cb != NULL && window->cb->pos_event != NULL) {
+				window->cb->pos_event(window->cb_arg,
+				    &event.ev.pos);
+			}
+			break;
+		}
 	}
 
Index: uspace/lib/display/test/display.c
===================================================================
--- uspace/lib/display/test/display.c	(revision 4645b2c34ead210c775e6151cfd474eff304e55a)
+++ uspace/lib/display/test/display.c	(revision b43edabea6b4e7a51e81261a5aec4d8b514e4e8f)
@@ -48,4 +48,5 @@
 static void test_display_conn(ipc_call_t *, void *);
 static void test_kbd_event(void *, kbd_event_t *);
+static void test_pos_event(void *, pos_event_t *);
 
 static errno_t test_window_create(void *, display_wnd_params_t *, sysarg_t *);
@@ -62,5 +63,6 @@
 
 static display_wnd_cb_t test_display_wnd_cb = {
-	.kbd_event = test_kbd_event
+	.kbd_event = test_kbd_event,
+	.pos_event = test_pos_event
 };
 
@@ -84,6 +86,7 @@
 	bool set_color_called;
 	bool kbd_event_called;
-	fibril_condvar_t kbd_event_cv;
-	fibril_mutex_t kbd_event_lock;
+	bool pos_event_called;
+	fibril_condvar_t event_cv;
+	fibril_mutex_t event_lock;
 	display_srv_t *srv;
 } test_response_t;
@@ -392,5 +395,4 @@
 	display_window_t *wnd;
 	test_response_t resp;
-	gfx_context_t *gc;
 
 	async_set_fallback_port_handler(test_display_conn, &resp);
@@ -421,36 +423,111 @@
 	PCUT_ASSERT_NOT_NULL(wnd);
 
-	gc = NULL;
-	rc = display_window_get_gc(wnd, &gc);
-	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
-	PCUT_ASSERT_NOT_NULL(gc);
-
 	resp.event_cnt = 1;
-	resp.event.kbd_event.type = KEY_PRESS;
-	resp.event.kbd_event.key = KC_ENTER;
-	resp.event.kbd_event.mods = 0;
-	resp.event.kbd_event.c = L'\0';
+	resp.event.etype = wev_kbd;
+	resp.event.ev.kbd.type = KEY_PRESS;
+	resp.event.ev.kbd.key = KC_ENTER;
+	resp.event.ev.kbd.mods = 0;
+	resp.event.ev.kbd.c = L'\0';
 	resp.wnd_id = wnd->id;
 	resp.kbd_event_called = false;
-	fibril_mutex_initialize(&resp.kbd_event_lock);
-	fibril_condvar_initialize(&resp.kbd_event_cv);
+	fibril_mutex_initialize(&resp.event_lock);
+	fibril_condvar_initialize(&resp.event_cv);
 	display_srv_ev_pending(resp.srv);
 
 	/* Wait for the event handler to be called. */
-	fibril_mutex_lock(&resp.kbd_event_lock);
+	fibril_mutex_lock(&resp.event_lock);
 	while (!resp.kbd_event_called) {
-		fibril_condvar_wait(&resp.kbd_event_cv, &resp.kbd_event_lock);
+		fibril_condvar_wait(&resp.event_cv, &resp.event_lock);
 	}
-	fibril_mutex_unlock(&resp.kbd_event_lock);
+	fibril_mutex_unlock(&resp.event_lock);
 
 	/* Verify that the event was delivered correctly */
-	PCUT_ASSERT_EQUALS(resp.event.kbd_event.type,
-	    resp.revent.kbd_event.type);
-	PCUT_ASSERT_EQUALS(resp.event.kbd_event.key,
-	    resp.revent.kbd_event.key);
-	PCUT_ASSERT_EQUALS(resp.event.kbd_event.mods,
-	    resp.revent.kbd_event.mods);
-	PCUT_ASSERT_EQUALS(resp.event.kbd_event.c,
-	    resp.revent.kbd_event.c);
+	PCUT_ASSERT_EQUALS(resp.event.etype,
+	    resp.revent.etype);
+	PCUT_ASSERT_EQUALS(resp.event.ev.kbd.type,
+	    resp.revent.ev.kbd.type);
+	PCUT_ASSERT_EQUALS(resp.event.ev.kbd.key,
+	    resp.revent.ev.kbd.key);
+	PCUT_ASSERT_EQUALS(resp.event.ev.kbd.mods,
+	    resp.revent.ev.kbd.mods);
+	PCUT_ASSERT_EQUALS(resp.event.ev.kbd.c,
+	    resp.revent.ev.kbd.c);
+
+	rc = display_window_destroy(wnd);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	display_close(disp);
+
+	rc = loc_service_unregister(sid);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+}
+
+/** Position event can be delivered from server to client callback function */
+PCUT_TEST(pos_event_deliver)
+{
+	errno_t rc;
+	service_id_t sid;
+	display_t *disp = NULL;
+	display_wnd_params_t params;
+	display_window_t *wnd;
+	test_response_t resp;
+
+	async_set_fallback_port_handler(test_display_conn, &resp);
+
+	// FIXME This causes this test to be non-reentrant!
+	rc = loc_server_register(test_display_server);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = loc_service_register(test_display_svc, &sid);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = display_open(test_display_svc, &disp);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+	PCUT_ASSERT_NOT_NULL(disp);
+	PCUT_ASSERT_NOT_NULL(resp.srv);
+
+	wnd = NULL;
+	resp.rc = EOK;
+	display_wnd_params_init(&params);
+	params.rect.p0.x = 0;
+	params.rect.p0.y = 0;
+	params.rect.p0.x = 100;
+	params.rect.p0.y = 100;
+
+	rc = display_window_create(disp, &params, &test_display_wnd_cb,
+	    (void *) &resp, &wnd);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+	PCUT_ASSERT_NOT_NULL(wnd);
+
+	resp.event_cnt = 1;
+	resp.event.etype = wev_pos;
+	resp.event.ev.pos.type = POS_PRESS;
+	resp.event.ev.pos.btn_num = 1;
+	resp.event.ev.pos.hpos = 2;
+	resp.event.ev.pos.vpos = 3;
+	resp.wnd_id = wnd->id;
+	resp.pos_event_called = false;
+	fibril_mutex_initialize(&resp.event_lock);
+	fibril_condvar_initialize(&resp.event_cv);
+	display_srv_ev_pending(resp.srv);
+
+	/* Wait for the event handler to be called. */
+	fibril_mutex_lock(&resp.event_lock);
+	while (!resp.pos_event_called) {
+		fibril_condvar_wait(&resp.event_cv, &resp.event_lock);
+	}
+	fibril_mutex_unlock(&resp.event_lock);
+
+	/* Verify that the event was delivered correctly */
+	PCUT_ASSERT_EQUALS(resp.event.etype,
+	    resp.revent.etype);
+	PCUT_ASSERT_EQUALS(resp.event.ev.pos.type,
+	    resp.revent.ev.pos.type);
+	PCUT_ASSERT_EQUALS(resp.event.ev.pos.btn_num,
+	    resp.revent.ev.pos.btn_num);
+	PCUT_ASSERT_EQUALS(resp.event.ev.pos.hpos,
+	    resp.revent.ev.pos.hpos);
+	PCUT_ASSERT_EQUALS(resp.event.ev.pos.vpos,
+	    resp.revent.ev.pos.vpos);
 
 	rc = display_window_destroy(wnd);
@@ -514,10 +591,24 @@
 	test_response_t *resp = (test_response_t *) arg;
 
-	resp->revent.kbd_event = *event;
-
-	fibril_mutex_lock(&resp->kbd_event_lock);
+	resp->revent.etype = wev_kbd;
+	resp->revent.ev.kbd = *event;
+
+	fibril_mutex_lock(&resp->event_lock);
 	resp->kbd_event_called = true;
-	fibril_condvar_broadcast(&resp->kbd_event_cv);
-	fibril_mutex_unlock(&resp->kbd_event_lock);
+	fibril_condvar_broadcast(&resp->event_cv);
+	fibril_mutex_unlock(&resp->event_lock);
+}
+
+static void test_pos_event(void *arg, pos_event_t *event)
+{
+	test_response_t *resp = (test_response_t *) arg;
+
+	resp->revent.etype = wev_pos;
+	resp->revent.ev.pos = *event;
+
+	fibril_mutex_lock(&resp->event_lock);
+	resp->pos_event_called = true;
+	fibril_condvar_broadcast(&resp->event_cv);
+	fibril_mutex_unlock(&resp->event_lock);
 }
 
