1 /*
2   Copyright 2012-2020 David Robillard <d@drobilla.net>
3 
4   Permission to use, copy, modify, and/or distribute this software for any
5   purpose with or without fee is hereby granted, provided that the above
6   copyright notice and this permission notice appear in all copies.
7 
8   THIS SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9   WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10   MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11   ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12   WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13   ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14   OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
16 
17 /*
18   Note that this header includes Vulkan headers, so if you are writing a
19   program or plugin that dynamically loads vulkan, you should first define
20   `VK_NO_PROTOTYPES` before including it.
21 */
22 
23 #ifndef PUGL_VULKAN_H
24 #define PUGL_VULKAN_H
25 
26 #include "pugl.h"
27 
28 #include <vulkan/vulkan_core.h>
29 
30 #include <stdint.h>
31 
32 PUGL_BEGIN_DECLS
33 
34 /**
35    @defgroup vulkan Vulkan
36    Vulkan graphics support.
37 
38    Vulkan support differs from OpenGL because almost all most configuration is
39    done using the Vulkan API itself, rather than by setting view hints to
40    configure the context.  Pugl only provides a minimal loader for loading the
41    Vulkan library, and a portable function to create a Vulkan surface for a
42    view, which hides the platform-specific implementation details.
43 
44    @ingroup pugl
45    @{
46 */
47 
48 /**
49    Dynamic Vulkan loader.
50 
51    This can be used to dynamically load the Vulkan library.  Applications or
52    plugins should not link against the Vulkan library, but instead use this at
53    runtime.  This ensures that things will work on as many systems as possible,
54    and allows errors to be handled gracefully.
55 
56    This is not a "loader" in the sense of loading all the required Vulkan
57    functions (which is the application's responsibility), but just a minimal
58    implementation to portably load the Vulkan library and get the two functions
59    that are used to load everything else.
60 
61    Note that this owns the loaded Vulkan library, so it must outlive all use of
62    the Vulkan API.
63 
64    @see https://www.khronos.org/registry/vulkan/specs/1.0/html/chap4.html
65 */
66 typedef struct PuglVulkanLoaderImpl PuglVulkanLoader;
67 
68 /**
69    Create a new dynamic loader for Vulkan functions.
70 
71    This dynamically loads the Vulkan library and gets the load functions from
72    it.
73 
74    @return A new Vulkan loader, or null on failure.
75 */
76 PUGL_API
77 PuglVulkanLoader*
78 puglNewVulkanLoader(PuglWorld* world);
79 
80 /**
81    Free a loader created with puglNewVulkanLoader().
82 
83    Note that this closes the Vulkan library, so no Vulkan objects or API may be
84    used after this is called.
85 */
86 PUGL_API
87 void
88 puglFreeVulkanLoader(PuglVulkanLoader* loader);
89 
90 /**
91    Return the `vkGetInstanceProcAddr` function.
92 
93    @return Null if the Vulkan library does not contain this function (which is
94    unlikely and indicates a broken system).
95 */
96 PUGL_API
97 PFN_vkGetInstanceProcAddr
98 puglGetInstanceProcAddrFunc(const PuglVulkanLoader* loader);
99 
100 /**
101    Return the `vkGetDeviceProcAddr` function.
102 
103    @return Null if the Vulkan library does not contain this function (which is
104    unlikely and indicates a broken system).
105 */
106 PUGL_API
107 PFN_vkGetDeviceProcAddr
108 puglGetDeviceProcAddrFunc(const PuglVulkanLoader* loader);
109 
110 /**
111    Return the Vulkan instance extensions required to draw to a PuglView.
112 
113    This simply returns static strings, it does not access Vulkan or the window
114    system.  The returned array always contains at least "VK_KHR_surface".
115 
116    @param[out] count The number of extensions in the returned array.
117    @return An array of extension name strings.
118 */
119 PUGL_API
120 const char* const*
121 puglGetInstanceExtensions(uint32_t* count);
122 
123 /**
124    Create a Vulkan surface for a Pugl view.
125 
126    @param vkGetInstanceProcAddr Accessor for Vulkan functions.
127    @param view The view the surface is to be displayed on.
128    @param instance The Vulkan instance.
129    @param allocator Vulkan allocation callbacks, may be NULL.
130    @param[out] surface Pointed to a newly created Vulkan surface.
131    @return `VK_SUCCESS` on success, or a Vulkan error code.
132 */
133 PUGL_API
134 VkResult
135 puglCreateSurface(PFN_vkGetInstanceProcAddr    vkGetInstanceProcAddr,
136                   PuglView*                    view,
137                   VkInstance                   instance,
138                   const VkAllocationCallbacks* allocator,
139                   VkSurfaceKHR*                surface);
140 
141 /**
142    Vulkan graphics backend.
143 
144    Pass the returned value to puglSetBackend() to draw to a view with Vulkan.
145 */
146 PUGL_CONST_API
147 const PuglBackend*
148 puglVulkanBackend(void);
149 
150 /**
151    @}
152 */
153 
154 PUGL_END_DECLS
155 
156 #endif // PUGL_VULKAN_H
157