(Android/Vulkan) Start hooking up Vulkan for Android context driver

This commit is contained in:
twinaphex 2016-03-01 18:16:22 +01:00
parent cbc575eec0
commit b8c1e31c13
2 changed files with 134 additions and 48 deletions

View File

@ -32,6 +32,10 @@
#include "../common/gl_common.h"
#endif
#ifdef HAVE_VULKAN
#include "../common/vulkan_common.h"
#endif
#include "../../frontend/drivers/platform_linux.h"
static enum gfx_ctx_api android_api;
@ -49,10 +53,47 @@ typedef struct
egl_ctx_data_t egl;
#endif
#ifdef HAVE_VULKAN
gfx_ctx_vulkan_data_t vk;
unsigned width;
unsigned height;
unsigned swap_interval;
#endif
} android_ctx_data_t;
static void android_gfx_ctx_destroy(void *data)
{
android_ctx_data_t *and = (android_ctx_data_t*)data;
#ifdef HAVE_VULKAN
struct android_app *android_app = (struct android_app*)g_android;
#endif
if (!and)
return;
switch (android_api)
{
case GFX_CTX_OPENGL_API:
case GFX_CTX_OPENGL_ES_API:
#ifdef HAVE_EGL
egl_destroy(&and->egl);
#endif
break;
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
vulkan_context_destroy(&and->vk, android_app->window);
if (and->vk.context.queue_lock)
slock_free(and->vk.context.queue_lock);
#endif
break;
case GFX_CTX_NONE:
default:
break;
}
free(data);
}
static void *android_gfx_ctx_init(void *video_driver)
{
#ifdef HAVE_OPENGLES
@ -94,6 +135,12 @@ static void *android_gfx_ctx_init(void *video_driver)
if (!egl_get_native_visual_id(&and->egl, &format))
goto error;
#endif
break;
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
if (!vulkan_context_init(&and->vk, VULKAN_WSI_ANDROID))
goto error;
#endif
break;
case GFX_CTX_NONE:
@ -120,6 +167,14 @@ static void *android_gfx_ctx_init(void *video_driver)
if (!egl_create_surface(&and->egl, android_app->window))
goto unlock_error;
#endif
break;
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
if (!vulkan_surface_create(&and->vk, VULKAN_WSI_ANDROID,
and->dpy, android_app->window,
and->width, and->height, and->swap_interval))
goto error;
#endif
break;
case GFX_CTX_NONE:
@ -133,52 +188,57 @@ static void *android_gfx_ctx_init(void *video_driver)
unlock_error:
slock_unlock(android_app->mutex);
error:
android_gfx_ctx_destroy(and);
return NULL;
}
static void android_gfx_ctx_get_video_size(void *data,
unsigned *width, unsigned *height)
{
android_ctx_data_t *and = (android_ctx_data_t*)data;
switch (android_api)
{
case GFX_CTX_OPENGL_API:
case GFX_CTX_OPENGL_ES_API:
#ifdef HAVE_EGL
egl_destroy(&and->egl);
egl_get_video_size(&and->egl, width, height);
#endif
break;
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
*width = and->width;
*height = and->height;
#endif
break;
case GFX_CTX_NONE:
default:
break;
}
return NULL;
}
static void android_gfx_ctx_destroy(void *data)
{
android_ctx_data_t *and = (android_ctx_data_t*)data;
if (!and)
return;
#ifdef HAVE_OPENGLES
egl_destroy(&and->egl);
#endif
free(data);
}
static void android_gfx_ctx_check_window(void *data, bool *quit,
bool *resize, unsigned *width, unsigned *height, unsigned frame_count)
{
unsigned new_width, new_height;
#ifdef HAVE_VULKAN
android_ctx_data_t *and = (android_ctx_data_t*)data;
#endif
(void)frame_count;
*quit = false;
android_gfx_ctx_get_video_size(data, &new_width, &new_height);
switch (android_api)
{
case GFX_CTX_OPENGL_API:
case GFX_CTX_OPENGL_ES_API:
#ifdef HAVE_OPENGLES
egl_get_video_size(&and->egl, &new_width, &new_height);
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
/* Swapchains are recreated in set_resize as a
* central place, so use that to trigger swapchain reinit. */
*resize = and->vk.need_new_swapchain;
#endif
break;
case GFX_CTX_NONE:
@ -224,10 +284,27 @@ static bool android_gfx_ctx_set_video_mode(void *data,
unsigned width, unsigned height,
bool fullscreen)
{
(void)data;
#ifdef HAVE_VULKAN
android_ctx_data_t *and = (android_ctx_data_t*)data;
#endif
(void)width;
(void)height;
(void)fullscreen;
switch (android_api)
{
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
and->width = width;
and->height = height;
#endif
break;
case GFX_CTX_NONE:
default:
break;
}
return true;
}
@ -351,6 +428,12 @@ static void android_gfx_ctx_swap_buffers(void *data)
case GFX_CTX_OPENVG_API:
#ifdef HAVE_EGL
egl_swap_buffers(&and->egl);
#endif
break;
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
vulkan_present(&and->vk, and->vk.context.current_swapchain_index);
vulkan_acquire_next_image(&and->vk);
#endif
break;
case GFX_CTX_NONE:
@ -371,23 +454,14 @@ static void android_gfx_ctx_set_swap_interval(void *data, unsigned swap_interval
egl_set_swap_interval(&and->egl, swap_interval);
#endif
break;
case GFX_CTX_NONE:
default:
break;
}
}
static void android_gfx_ctx_get_video_size(void *data,
unsigned *width, unsigned *height)
{
android_ctx_data_t *and = (android_ctx_data_t*)data;
switch (android_api)
{
case GFX_CTX_OPENGL_API:
case GFX_CTX_OPENGL_ES_API:
#ifdef HAVE_EGL
egl_get_video_size(&and->egl, width, height);
case GFX_CTX_VULKAN_API:
#ifdef HAVE_VULKAN
if (and->swap_interval != swap_interval)
{
and->swap_interval = swap_interval;
if (and->vk.swapchain)
and->vk.need_new_swapchain = true;
}
#endif
break;
case GFX_CTX_NONE:
@ -396,6 +470,7 @@ static void android_gfx_ctx_get_video_size(void *data,
}
}
static gfx_ctx_proc_t android_gfx_ctx_get_proc_address(const char *symbol)
{
switch (android_api)
@ -433,6 +508,14 @@ static void android_gfx_ctx_bind_hw_render(void *data, bool enable)
}
}
#ifdef HAVE_VULKAN
static void *android_gfx_ctx_get_context_data(void *data)
{
android_ctx_data_t *and = (android_ctx_data_t*)data;
return &and->vk.context;
}
#endif
const gfx_ctx_driver_t gfx_ctx_android = {
android_gfx_ctx_init,
android_gfx_ctx_destroy,
@ -459,4 +542,9 @@ const gfx_ctx_driver_t gfx_ctx_android = {
NULL,
"android",
android_gfx_ctx_bind_hw_render,
#ifdef HAVE_VULKAN
android_gfx_ctx_get_context_data
#else
NULL
#endif
};

View File

@ -242,7 +242,13 @@ static const struct wl_registry_listener registry_listener = {
};
static void gfx_ctx_wl_get_video_size(void *data,
unsigned *width, unsigned *height);
unsigned *width, unsigned *height)
{
gfx_ctx_wayland_data_t *wl = (gfx_ctx_wayland_data_t*)data;
*width = wl->width;
*height = wl->height;
}
static void gfx_ctx_wl_destroy_resources(gfx_ctx_wayland_data_t *wl)
{
@ -422,14 +428,6 @@ static void gfx_ctx_wl_update_window_title(void *data)
runloop_msg_queue_push(buf_fps, 1, 1, false);
}
static void gfx_ctx_wl_get_video_size(void *data,
unsigned *width, unsigned *height)
{
gfx_ctx_wayland_data_t *wl = (gfx_ctx_wayland_data_t*)data;
*width = wl->width;
*height = wl->height;
}
static bool gfx_ctx_wl_get_metrics(void *data,
enum display_metric_types type, float *value)