[gtk+/wip/otte/vulkan: 25/28] vulkan: Expose the swapchain images in public API
- From: Benjamin Otte <otte src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk+/wip/otte/vulkan: 25/28] vulkan: Expose the swapchain images in public API
- Date: Sun, 4 Dec 2016 17:01:08 +0000 (UTC)
commit af59be884f2ef0cfd08529f1a37d9011a3299940
Author: Benjamin Otte <otte redhat com>
Date: Wed Nov 30 00:54:48 2016 +0100
vulkan: Expose the swapchain images in public API
gdk/gdkvulkancontext.c | 90 +++++++++++++++++++++++++++++++++++++++++++++---
gdk/gdkvulkancontext.h | 5 +++
2 files changed, 90 insertions(+), 5 deletions(-)
---
diff --git a/gdk/gdkvulkancontext.c b/gdk/gdkvulkancontext.c
index 9c913da..e28ef62 100644
--- a/gdk/gdkvulkancontext.c
+++ b/gdk/gdkvulkancontext.c
@@ -36,10 +36,21 @@ struct _GdkVulkanContextPrivate {
int swapchain_width, swapchain_height;
VkSwapchainKHR swapchain;
+
+ guint n_images;
+ VkImage *images;
+};
+
+enum {
+ IMAGES_UPDATED,
+
+ LAST_SIGNAL
};
G_DEFINE_QUARK (gdk-vulkan-error-quark, gdk_vulkan_error)
+static guint signals[LAST_SIGNAL] = { 0 };
+
static void gdk_vulkan_context_initable_init (GInitableIface *iface);
G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GdkVulkanContext, gdk_vulkan_context, GDK_TYPE_DRAW_CONTEXT,
@@ -111,6 +122,9 @@ gdk_vulkan_context_dispose (GObject *gobject)
GdkVulkanContextPrivate *priv = gdk_vulkan_context_get_instance_private (context);
GdkDisplay *display;
+ g_clear_pointer (&priv->images, g_free);
+ priv->n_images = 0;
+
if (priv->swapchain != VK_NULL_HANDLE)
{
vkDestroySwapchainKHR (gdk_vulkan_context_get_device (context),
@@ -141,6 +155,23 @@ gdk_vulkan_context_class_init (GdkVulkanContextClass *klass)
GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
gobject_class->dispose = gdk_vulkan_context_dispose;
+
+ /**
+ * GdkVulkanContext::images-updated:
+ * @context: the object on which the signal is emitted
+ *
+ * This signal is emitted when the images managed by this context have
+ * changed. Usually this means that the swapchain had to be recreated,
+ * for example in response to a change of the window size.
+ */
+ signals[IMAGES_UPDATED] =
+ g_signal_new (g_intern_static_string ("images-updated"),
+ G_OBJECT_CLASS_TYPE (gobject_class),
+ G_SIGNAL_RUN_LAST,
+ 0,
+ NULL, NULL,
+ g_cclosure_marshal_VOID__VOID,
+ G_TYPE_NONE, 0);
}
static void
@@ -156,12 +187,15 @@ gdk_vulkan_context_check_swapchain (GdkVulkanContext *context,
GdkWindow *window = gdk_draw_context_get_window (GDK_DRAW_CONTEXT (context));
VkSwapchainKHR new_swapchain;
VkResult res;
+ VkDevice device;
if (gdk_window_get_width (window) == priv->swapchain_width &&
gdk_window_get_height (window) == priv->swapchain_height)
return TRUE;
- res = GDK_VK_CHECK (vkCreateSwapchainKHR, gdk_vulkan_context_get_device (context),
+ device = gdk_vulkan_context_get_device (context);
+
+ res = GDK_VK_CHECK (vkCreateSwapchainKHR, device,
&(VkSwapchainCreateInfoKHR) {
.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR,
.pNext = NULL,
@@ -191,15 +225,29 @@ gdk_vulkan_context_check_swapchain (GdkVulkanContext *context,
&new_swapchain);
if (priv->swapchain != VK_NULL_HANDLE)
- vkDestroySwapchainKHR (gdk_vulkan_context_get_device (context),
- priv->swapchain,
- NULL);
+ {
+ vkDestroySwapchainKHR (device,
+ priv->swapchain,
+ NULL);
+ g_clear_pointer (&priv->images, g_free);
+ priv->n_images = 0;
+ }
if (res == VK_SUCCESS)
{
priv->swapchain_width = gdk_window_get_width (window);
priv->swapchain_height = gdk_window_get_height (window);
priv->swapchain = new_swapchain;
+
+ GDK_VK_CHECK (vkGetSwapchainImagesKHR, device,
+ priv->swapchain,
+ &priv->n_images,
+ NULL);
+ priv->images = g_new (VkImage, priv->n_images);
+ GDK_VK_CHECK (vkGetSwapchainImagesKHR, device,
+ priv->swapchain,
+ &priv->n_images,
+ priv->images);
}
else
{
@@ -211,7 +259,9 @@ gdk_vulkan_context_check_swapchain (GdkVulkanContext *context,
return FALSE;
}
- return TRUE;
+ g_signal_emit (context, signals[IMAGES_UPDATED], 0);
+
+ return res == VK_SUCCESS;
}
static gboolean
@@ -317,6 +367,28 @@ gdk_vulkan_context_get_image_format (GdkVulkanContext *context)
return priv->image_format.format;
}
+guint
+gdk_vulkan_context_get_n_images (GdkVulkanContext *context)
+{
+ GdkVulkanContextPrivate *priv = gdk_vulkan_context_get_instance_private (context);
+
+ g_return_val_if_fail (GDK_IS_VULKAN_CONTEXT (context), 0);
+
+ return priv->n_images;
+}
+
+VkImage
+gdk_vulkan_context_get_image (GdkVulkanContext *context,
+ guint id)
+{
+ GdkVulkanContextPrivate *priv = gdk_vulkan_context_get_instance_private (context);
+
+ g_return_val_if_fail (GDK_IS_VULKAN_CONTEXT (context), VK_NULL_HANDLE);
+ g_return_val_if_fail (id < priv->n_images, VK_NULL_HANDLE);
+
+ return priv->images[id];
+}
+
static gboolean
gdk_display_create_vulkan_device (GdkDisplay *display,
GError **error)
@@ -622,6 +694,14 @@ gdk_display_unref_vulkan (GdkDisplay *display)
static void
gdk_vulkan_context_class_init (GdkVulkanContextClass *klass)
{
+ signals[IMAGES_UPDATED] =
+ g_signal_new (g_intern_static_string ("images-updated"),
+ G_OBJECT_CLASS_TYPE (object_class),
+ G_SIGNAL_RUN_LAST,
+ NULL,
+ NULL, NULL,
+ g_cclosure_marshal_VOID__VOID,
+ G_TYPE_NONE, 0);
}
static void
diff --git a/gdk/gdkvulkancontext.h b/gdk/gdkvulkancontext.h
index 8bce304..b40257b 100644
--- a/gdk/gdkvulkancontext.h
+++ b/gdk/gdkvulkancontext.h
@@ -61,6 +61,11 @@ GDK_AVAILABLE_IN_3_90
VkQueue gdk_vulkan_context_get_queue (GdkVulkanContext *context);
GDK_AVAILABLE_IN_3_90
VkFormat gdk_vulkan_context_get_image_format (GdkVulkanContext *context);
+GDK_AVAILABLE_IN_3_90
+guint gdk_vulkan_context_get_n_images (GdkVulkanContext *context);
+GDK_AVAILABLE_IN_3_90
+VkImage gdk_vulkan_context_get_image (GdkVulkanContext *context,
+ guint id);
#endif /* GDK_WINDOWING_VULKAN */
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]