[gtk+/wip/otte/vulkan: 31/62] gskvulkanrenderer: Create imagevies and framebuffers



commit 3e59b11700c88867d34c51459ef119b137992da1
Author: Benjamin Otte <otte redhat com>
Date:   Wed Nov 30 02:08:17 2016 +0100

    gskvulkanrenderer: Create imagevies and framebuffers

 gsk/gskvulkanrenderer.c |  143 ++++++++++++++++++++++++++++++++++++++++++++++-
 1 files changed, 141 insertions(+), 2 deletions(-)
---
diff --git a/gsk/gskvulkanrenderer.c b/gsk/gskvulkanrenderer.c
index 32fefcd..f51806f 100644
--- a/gsk/gskvulkanrenderer.c
+++ b/gsk/gskvulkanrenderer.c
@@ -8,6 +8,8 @@
 #include "gskrendernodeprivate.h"
 #include "gsktextureprivate.h"
 
+typedef struct _GskVulkanTarget GskVulkanTarget;
+
 #ifdef G_ENABLE_DEBUG
 typedef struct {
   GQuark cpu_time;
@@ -20,6 +22,11 @@ struct _GskVulkanRenderer
   GskRenderer parent_instance;
 
   GdkVulkanContext *vulkan;
+
+  guint n_targets;
+  GskVulkanTarget **targets;
+  VkRenderPass render_pass;
+
 #ifdef G_ENABLE_DEBUG
   ProfileTimers profile_timers;
 #endif
@@ -32,10 +39,132 @@ struct _GskVulkanRendererClass
 
 G_DEFINE_TYPE (GskVulkanRenderer, gsk_vulkan_renderer, GSK_TYPE_RENDERER)
 
+struct _GskVulkanTarget {
+  VkImage image;
+  VkImageView image_view;
+  VkFramebuffer framebuffer;
+}; 
+
+static inline VkResult
+gsk_vulkan_handle_result (VkResult    res,
+                          const char *called_function)
+{
+  if (res != VK_SUCCESS)
+    {
+      GSK_NOTE (VULKAN,g_printerr ("%s(): %s (%d)\n", called_function, gdk_vulkan_strerror (res), res));
+    }
+  return res;
+}
+
+#define GSK_VK_CHECK(func, ...) gsk_vulkan_handle_result (func (__VA_ARGS__), G_STRINGIFY (func))
+
+static GskVulkanTarget *
+gsk_vulkan_target_new_for_image (GskVulkanRenderer *self,
+                                 VkImage            image)
+{
+  GskVulkanTarget *target;
+  GdkWindow *window;
+  VkDevice device;
+
+  device = gdk_vulkan_context_get_device (self->vulkan);
+  window = gdk_draw_context_get_window (GDK_DRAW_CONTEXT (self->vulkan));
+
+  target = g_slice_new0 (GskVulkanTarget);
+
+  target->image = image;
+
+  GSK_VK_CHECK (vkCreateImageView, device,
+                                   &(VkImageViewCreateInfo) {
+                                       .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
+                                       .image = target->image,
+                                       .viewType = VK_IMAGE_VIEW_TYPE_2D,
+                                       .format = gdk_vulkan_context_get_image_format (self->vulkan),
+                                       .components = {
+                                           .r = VK_COMPONENT_SWIZZLE_R,
+                                           .g = VK_COMPONENT_SWIZZLE_G,
+                                           .b = VK_COMPONENT_SWIZZLE_B,
+                                           .a = VK_COMPONENT_SWIZZLE_A,
+                                       },
+                                       .subresourceRange = {
+                                           .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
+                                           .baseMipLevel = 0,
+                                           .levelCount = 1,
+                                           .baseArrayLayer = 0,
+                                           .layerCount = 1,
+                                       },
+                                   },
+                                   NULL,
+                                   &target->image_view);
+  GSK_VK_CHECK (vkCreateFramebuffer, device,
+                                     &(VkFramebufferCreateInfo) {
+                                         .sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
+                                         .renderPass = self->render_pass,
+                                         .attachmentCount = 1,
+                                         .pAttachments = &target->image_view,
+                                         .width = gdk_window_get_width (window),
+                                         .height = gdk_window_get_height (window),
+                                         .layers = 1
+                                     },
+                                     NULL,
+                                     &target->framebuffer);
+
+  return target;
+}
+
+static void
+gsk_vulkan_target_free (GskVulkanRenderer *self,
+                        GskVulkanTarget   *target)
+{
+  VkDevice device;
+
+  device = gdk_vulkan_context_get_device (self->vulkan);
+
+  vkDestroyFramebuffer (device,
+                        target->framebuffer,
+                        NULL);
+  vkDestroyImageView (device,
+                      target->image_view,
+                      NULL);
+
+  g_slice_free (GskVulkanTarget, target);
+}
+
+static void
+gsk_vulkan_renderer_free_targets (GskVulkanRenderer *self)
+{
+  guint i;
+
+  for (i = 0; i < self->n_targets; i++)
+    {
+      gsk_vulkan_target_free (self, self->targets[i]);
+    }
+
+  g_clear_pointer (&self->targets, g_free);
+  self->n_targets = 0;
+}
+
+static void
+gsk_vulkan_renderer_update_images_cb (GdkVulkanContext  *context,
+                                      GskVulkanRenderer *self)
+{
+  guint i;
+
+  gsk_vulkan_renderer_free_targets (self);
+
+  self->n_targets = gdk_vulkan_context_get_n_images (context);
+  self->targets = g_new (GskVulkanTarget *, self->n_targets);
+
+  for (i = 0; i < self->n_targets; i++)
+    {
+      self->targets[i] = gsk_vulkan_target_new_for_image (self,
+                                                          gdk_vulkan_context_get_image (context, i));
+    }
+}
+
 static gboolean
 gsk_vulkan_renderer_realize (GskRenderer  *renderer,
-                            GdkWindow    *window,
-                            GError      **error)
+                             GdkWindow    *window,
+                             GError      **error)
 {
   GskVulkanRenderer *self = GSK_VULKAN_RENDERER (renderer);
 
@@ -43,6 +172,12 @@ gsk_vulkan_renderer_realize (GskRenderer  *renderer,
   if (self->vulkan == NULL)
     return FALSE;
 
+  g_signal_connect (self->vulkan,
+                    "images-updated",
+                    G_CALLBACK (gsk_vulkan_renderer_update_images_cb),
+                    self);
+  gsk_vulkan_renderer_update_images_cb (self->vulkan, self);
+
   return TRUE;
 }
 
@@ -51,6 +186,10 @@ gsk_vulkan_renderer_unrealize (GskRenderer *renderer)
 {
   GskVulkanRenderer *self = GSK_VULKAN_RENDERER (renderer);
 
+  gsk_vulkan_renderer_free_targets (self);
+  g_signal_handlers_disconnect_by_func(self->vulkan,
+                                       gsk_vulkan_renderer_update_images_cb,
+                                       self);
   g_clear_object (&self->vulkan);
 }
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]