annotate svk/api.nim @ 1489:e6bd1f553c1b default tip main

add: quite a bit more wrapper
author sam <sam@basx.dev>
date Sun, 18 May 2025 23:47:16 +0700
parents 3ce7c132fdac
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1488
3ce7c132fdac did: improvments
sam <sam@basx.dev>
parents: 1487
diff changeset
1 import std/sequtils
3ce7c132fdac did: improvments
sam <sam@basx.dev>
parents: 1487
diff changeset
2 import std/enumutils
1487
f786797a0cbe did: stuff
sam <sam@basx.dev>
parents: 1486
diff changeset
3 import std/tables
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
4 import std/strutils
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
5 import std/logging
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
6 import std/os
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
7
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
8 include ./vkapi
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
9
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
10 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
11 # UTILS =======================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
12 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
13
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
14 if not defined(release):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
15 addHandler(newConsoleLogger())
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
16 addHandler(newFileLogger("svk.log"))
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
17
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
18 # log level
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
19 when defined(release):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
20 const LOGLEVEL {.strdefine.}: string = "Warn"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
21 else:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
22 const LOGLEVEL {.strdefine.}: string = "Debug"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
23 setLogFilter(parseEnum[Level]("lvl" & LOGLEVEL))
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
24
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
25 template debugAssert(arg: untyped): untyped =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
26 when not defined(release):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
27 assert arg
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
28
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
29 # we will support vulkan 1.2 for maximum portability
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
30 const VULKAN_VERSION = VK_MAKE_API_VERSION(0, 1, 2, 0)
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
31
1488
3ce7c132fdac did: improvments
sam <sam@basx.dev>
parents: 1487
diff changeset
32 iterator items*[T: HoleyEnum](E: typedesc[T]): T =
3ce7c132fdac did: improvments
sam <sam@basx.dev>
parents: 1487
diff changeset
33 for a in enumFullRange(E):
3ce7c132fdac did: improvments
sam <sam@basx.dev>
parents: 1487
diff changeset
34 yield a
3ce7c132fdac did: improvments
sam <sam@basx.dev>
parents: 1487
diff changeset
35
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
36 template checkVkResult*(call: untyped) =
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
37 when defined(release):
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
38 discard call
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
39 else:
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
40 # yes, a bit cheap, but this is only for nice debug output
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
41 var callstr = astToStr(call).replace("\n", "")
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
42 while callstr.find(" ") >= 0:
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
43 callstr = callstr.replace(" ", " ")
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
44 debug "Calling vulkan: ", callstr
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
45 let value = call
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
46 if value != VK_SUCCESS:
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
47 error "Vulkan error: ", astToStr(call), " returned ", $value
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
48 raise newException(
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
49 Exception, "Vulkan error: " & astToStr(call) & " returned " & $value
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
50 )
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
51
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
52 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
53 # PLATFORM TYPES ==============================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
54 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
55
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
56 when defined(windows):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
57 type NativeWindow* = object
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
58 hinstance*: HINSTANCE
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
59 hwnd*: HWND
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
60 g_wpPrev*: WINDOWPLACEMENT
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
61 else:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
62 type NativeWindow* = object
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
63 display*: ptr Display
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
64 window*: Window
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
65 emptyCursor*: Cursor
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
66 ic*: XIC
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
67
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
68
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
69
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
70
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
71 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
72 # VULKAN INSTANCE =============================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
73 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
74
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
75 type SVkInstance* = object
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
76 vkInstance: VkInstance
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
77 debugMessenger: VkDebugUtilsMessengerEXT
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
78 window: NativeWindow
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
79 vkSurface*: VkSurfaceKHR
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
80
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
81 proc createWindow(title: string): NativeWindow
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
82
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
83 proc `=copy`(a: var SVkInstance, b: SVkInstance) {.error.}
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
84
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
85 proc `=destroy`(a: SVkInstance) =
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
86 debugAssert a.vkInstance.pointer == nil
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
87 debugAssert a.vkSurface.pointer == nil
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
88 debugAssert a.debugMessenger.pointer == nil
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
89
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
90 proc destroy*(a: var SVkInstance) =
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
91 if a.vkInstance.pointer != nil:
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
92 if a.debugMessenger.pointer != nil:
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
93 vkDestroyDebugUtilsMessengerEXT(a.vkInstance, a.debugMessenger, nil)
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
94 a.debugMessenger = VkDebugUtilsMessengerEXT(nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
95 vkDestroySurfaceKHR(a.vkInstance, a.vkSurface, nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
96 a.vkSurface = VkSurfaceKHR(nil)
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
97 a.vkInstance.vkDestroyInstance(nil)
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
98 a.vkInstance = VkInstance(nil)
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
99
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
100 proc debugCallback(
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
101 messageSeverity: VkDebugUtilsMessageSeverityFlagBitsEXT,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
102 messageTypes: VkDebugUtilsMessageTypeFlagsEXT,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
103 pCallbackData: ptr VkDebugUtilsMessengerCallbackDataEXT,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
104 userData: pointer,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
105 ): VkBool32 {.cdecl.} =
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
106 const LOG_LEVEL_MAPPING = {
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
107 VK_DEBUG_UTILS_MESSAGE_SEVERITY_VERBOSE_BIT_EXT: lvlDebug,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
108 VK_DEBUG_UTILS_MESSAGE_SEVERITY_INFO_BIT_EXT: lvlInfo,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
109 VK_DEBUG_UTILS_MESSAGE_SEVERITY_WARNING_BIT_EXT: lvlWarn,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
110 VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT: lvlError,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
111 }.toTable
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
112 log LOG_LEVEL_MAPPING[messageSeverity], "SVK-LOG: ", $pCallbackData.pMessage
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
113 if messageSeverity == VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT:
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
114 let errorMsg = $pCallbackData.pMessage & ": " & getStackTrace()
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
115 raise newException(Exception, errorMsg)
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
116 return VK_FALSE
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
117
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
118 proc svkCreateInstance*(
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
119 applicationName: string,
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
120 enabledLayers: openArray[string] = [],
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
121 enabledExtensions: openArray[string] =
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
122 if defined(release):
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
123 if defined(windows):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
124 @["VK_KHR_surface", "VK_KHR_win32_surface"]
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
125 else:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
126 @["VK_KHR_surface", "VK_KHR_xlib_surface"]
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
127 else:
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
128 if defined(windows):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
129 @["VK_KHR_surface", "VK_EXT_debug_utils", "VK_KHR_win32_surface"]
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
130 else:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
131 @["VK_KHR_surface", "VK_EXT_debug_utils", "VK_KHR_xlib_surface"],
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
132 engineName = "semicongine",
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
133 ): SVkInstance =
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
134 putEnv("VK_LOADER_LAYERS_ENABLE", "*validation")
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
135 putEnv(
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
136 "VK_LAYER_ENABLES",
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
137 "VALIDATION_CHECK_ENABLE_VENDOR_SPECIFIC_AMD,VALIDATION_CHECK_ENABLE_VENDOR_SPECIFIC_NVIDIA,VK_VALIDATION_FEATURE_ENABLE_SYNCHRONIZATION_VALIDATION_EXTVK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_EXT,VK_VALIDATION_FEATURE_ENABLE_SYNCHRONIZATION_VALIDATION_EXT",
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
138 )
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
139 initVulkanLoader()
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
140
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
141 var allLayers = @enabledLayers
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
142 when not defined(release):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
143 allLayers.add "VK_LAYER_KHRONOS_validation"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
144
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
145 let
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
146 appinfo = VkApplicationInfo(
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
147 pApplicationName: applicationName,
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
148 pEngineName: engineName,
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
149 apiVersion: VULKAN_VERSION,
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
150 )
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
151 enabledLayersC = allocCStringArray(allLayers)
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
152 enabledExtensionsC = allocCStringArray(enabledExtensions)
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
153 createinfo = VkInstanceCreateInfo(
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
154 pApplicationInfo: addr appinfo,
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
155 enabledLayerCount: allLayers.len.uint32,
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
156 ppEnabledLayerNames: enabledLayersC,
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
157 enabledExtensionCount: enabledExtensions.len.uint32,
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
158 ppEnabledExtensionNames: enabledExtensionsC,
1485
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
159 )
6e062a84c157 add: more api-starting
sam <sam@basx.dev>
parents:
diff changeset
160 checkVkResult vkCreateInstance(addr createinfo, nil, addr result.vkInstance)
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
161
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
162 enabledLayersC.deallocCStringArray()
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
163 enabledExtensionsC.deallocCStringArray()
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
164
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
165 # only support up to vulkan 1.2 for maximum portability
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
166 load_VK_VERSION_1_0(result.vkInstance)
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
167 load_VK_VERSION_1_1(result.vkInstance)
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
168 load_VK_VERSION_1_2(result.vkInstance)
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
169
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
170 for extension in enabledExtensions:
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
171 loadExtension(result.vkInstance, extension)
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
172 load_VK_KHR_swapchain(result.vkInstance)
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
173
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
174 var allTypes: VkDebugUtilsMessageTypeFlagsEXT
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
175 for t in VkDebugUtilsMessageTypeFlagBitsEXT:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
176 allTypes = allTypes or t
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
177 when not defined(release):
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
178 var debugMessengerCreateInfo = VkDebugUtilsMessengerCreateInfoEXT(
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
179 messageSeverity: VK_DEBUG_UTILS_MESSAGE_SEVERITY_VERBOSE_BIT_EXT or VK_DEBUG_UTILS_MESSAGE_SEVERITY_INFO_BIT_EXT or VK_DEBUG_UTILS_MESSAGE_SEVERITY_WARNING_BIT_EXT or VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
180 messageType: VK_DEBUG_UTILS_MESSAGE_TYPE_GENERAL_BIT_EXT or VK_DEBUG_UTILS_MESSAGE_TYPE_VALIDATION_BIT_EXT or VK_DEBUG_UTILS_MESSAGE_TYPE_PERFORMANCE_BIT_EXT,
1486
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
181 pfnUserCallback: debugCallback,
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
182 )
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
183 checkVkResult vkCreateDebugUtilsMessengerEXT(
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
184 result.vkInstance, addr debugMessengerCreateInfo, nil, addr result.debugMessenger
0ba3f0b2be2e did: more
sam <sam@basx.dev>
parents: 1485
diff changeset
185 )
1489
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
186
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
187
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
188 result.window = createWindow(applicationName)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
189 when defined(windows):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
190 var surfaceCreateInfo = VkWin32SurfaceCreateInfoKHR(hinstance: window.hinstance, hwnd: window.hwnd)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
191 checkVkResult vkCreateWin32SurfaceKHR(instance, addr surfaceCreateInfo, nil, addr result.vkSurface)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
192 else:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
193 var surfaceCreateInfo = VkXlibSurfaceCreateInfoKHR(dpy: result.window.display, window: result.window.window)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
194 checkVkResult result.vkInstance.vkCreateXlibSurfaceKHR(addr surfaceCreateInfo, nil, addr result.vkSurface)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
195
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
196
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
197
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
198 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
199 # PHYSICAL DEVICES ============================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
200 # =============================================================================
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
201
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
202 type
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
203 SVkMemoryType* = object
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
204 size: uint64
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
205 deviceLocal: bool # fast for gpu access
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
206 hostCached: bool # fast for host access
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
207 hostVisible: bool # can use vkMapMemory
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
208 hostCohorent: bool # does *not* require vkFlushMappedMemoryRanges and vkInvalidateMappedMemoryRanges
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
209 SVkQueueFamilies* = object
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
210 count: int
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
211 hasGraphics: bool # implies "hasTransfer"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
212 hasCompute: bool # implies "hasTransfer"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
213
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
214 SVkPhysicalDevice* = object
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
215 name*: string
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
216 vkPhysicalDevice*: VkPhysicalDevice
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
217 vkPhysicalDeviceFeatures*: VkPhysicalDeviceFeatures
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
218 vkPhysicalDeviceProperties*: VkPhysicalDeviceProperties
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
219 memoryTypes*: seq[SVkMemoryType]
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
220 queueFamily*: uint32
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
221
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
222 proc getUsablePhysicalDevices*(instance: SVkInstance): seq[SVkPhysicalDevice] =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
223 var nDevices: uint32
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
224 checkVkResult instance.vkInstance.vkEnumeratePhysicalDevices(addr nDevices, nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
225 var devices = newSeq[VkPhysicalDevice](nDevices)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
226 checkVkResult instance.vkInstance.vkEnumeratePhysicalDevices(addr nDevices, addr devices[0])
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
227 for d in devices:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
228 var dev = SVkPhysicalDevice(vkPhysicalDevice: d)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
229 d.vkGetPhysicalDeviceFeatures(addr dev.vkPhysicalDeviceFeatures)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
230 d.vkGetPhysicalDeviceProperties(addr dev.vkPhysicalDeviceProperties)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
231
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
232 if dev.vkPhysicalDeviceProperties.deviceType notin [VK_PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU, VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU]:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
233 continue
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
234 dev.name = $cast[cstring](addr dev.vkPhysicalDeviceProperties.deviceName[0])
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
235
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
236 var memoryProperties: VkPhysicalDeviceMemoryProperties
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
237 d.vkGetPhysicalDeviceMemoryProperties(addr memoryProperties)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
238 for i in 0 ..< memoryProperties.memoryTypeCount:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
239 let heapI = memoryProperties.memoryTypes[i].heapIndex
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
240 dev.memoryTypes.add SVkMemoryType(
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
241 size: memoryProperties.memoryHeaps[heapI].size.uint64,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
242 deviceLocal: VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT in memoryProperties.memoryTypes[i].propertyFlags,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
243 hostCached: VK_MEMORY_PROPERTY_HOST_CACHED_BIT in memoryProperties.memoryTypes[i].propertyFlags,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
244 hostVisible: VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT in memoryProperties.memoryTypes[i].propertyFlags,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
245 hostCohorent: VK_MEMORY_PROPERTY_HOST_COHERENT_BIT in memoryProperties.memoryTypes[i].propertyFlags,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
246 )
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
247
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
248
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
249 var familyQueueCount: uint32
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
250 var vkQueueFamilyProperties: seq[VkQueueFamilyProperties]
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
251 d.vkGetPhysicalDeviceQueueFamilyProperties(addr familyQueueCount, nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
252 vkQueueFamilyProperties.setLen(familyQueueCount)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
253 d.vkGetPhysicalDeviceQueueFamilyProperties(addr familyQueueCount, addr vkQueueFamilyProperties[0])
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
254 dev.queueFamily = high(uint32)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
255 for i in 0 ..< familyQueueCount:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
256 let hasGraphics = VK_QUEUE_GRAPHICS_BIT in vkQueueFamilyProperties[i].queueFlags
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
257 let hasCompute = VK_QUEUE_COMPUTE_BIT in vkQueueFamilyProperties[i].queueFlags
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
258 let hasPresentation = VK_FALSE
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
259 checkVkResult dev.vkPhysicalDevice.vkGetPhysicalDeviceSurfaceSupportKHR(i, instance.vkSurface, addr hasPresentation)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
260
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
261 if hasGraphics and hasCompute and bool(hasPresentation):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
262 dev.queueFamily = i
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
263 break
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
264 if dev.queueFamily == high(uint32):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
265 raise newException(Exception, "Did not find queue family with graphics and compute support!")
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
266
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
267 result.add dev
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
268
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
269 when defined(windows):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
270 proc createWindow(title: string): NativeWindow =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
271 result.hInstance = HINSTANCE(GetModuleHandle(nil))
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
272 var
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
273 windowClassName = T"EngineWindowClass"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
274 windowName = T(title)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
275 windowClass = WNDCLASSEX(
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
276 cbSize: UINT(WNDCLASSEX.sizeof),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
277 lpfnWndProc: windowHandler,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
278 hInstance: result.hInstance,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
279 lpszClassName: windowClassName,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
280 hcursor: currentCursor,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
281 )
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
282
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
283 if (RegisterClassEx(addr(windowClass)) == 0):
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
284 raise newException(Exception, "Unable to register window class")
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
285
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
286 result.hwnd = CreateWindowEx(
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
287 DWORD(0),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
288 windowClassName,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
289 windowName,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
290 DWORD(WS_OVERLAPPEDWINDOW),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
291 CW_USEDEFAULT,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
292 CW_USEDEFAULT,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
293 CW_USEDEFAULT,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
294 CW_USEDEFAULT,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
295 HMENU(0),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
296 HINSTANCE(0),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
297 result.hInstance,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
298 nil,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
299 )
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
300
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
301 result.g_wpPrev.length = UINT(sizeof(WINDOWPLACEMENT))
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
302 discard result.hwnd.ShowWindow(SW_SHOW)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
303 discard result.hwnd.SetForegroundWindow()
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
304 discard result.hwnd.SetFocus()
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
305
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
306 proc destroyWindow*(window: NativeWindow) =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
307 DestroyWindow(window.hwnd)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
308
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
309 else:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
310 import ../semicongine/thirdparty/x11/xkblib
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
311 import ../semicongine/thirdparty/x11/xutil
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
312
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
313 var deleteMessage* {.hint[GlobalVar]: off.}: x.Atom # one internal use, not serious
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
314
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
315 proc XErrorLogger(display: PDisplay, event: PXErrorEvent): cint {.cdecl.} =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
316 logging.error "Xlib: " & $event[]
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
317
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
318 proc createWindow(title: string): NativeWindow =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
319 doAssert XInitThreads() != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
320 let display = XOpenDisplay(nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
321 if display == nil:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
322 quit "Failed to open display"
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
323 discard XSetErrorHandler(XErrorLogger)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
324
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
325 let screen = display.XDefaultScreen()
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
326 let rootWindow = display.XRootWindow(screen)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
327 let vis = display.XDefaultVisual(screen)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
328 discard display.XkbSetDetectableAutoRepeat(true, nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
329 var
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
330 attribs: XWindowAttributes
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
331 width = cuint(800)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
332 height = cuint(600)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
333 doAssert display.XGetWindowAttributes(rootWindow, addr(attribs)) != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
334
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
335 var attrs = XSetWindowAttributes(
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
336 event_mask:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
337 FocusChangeMask or KeyPressMask or KeyReleaseMask or ExposureMask or
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
338 VisibilityChangeMask or StructureNotifyMask or ButtonMotionMask or ButtonPressMask or
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
339 ButtonReleaseMask
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
340 )
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
341 let window = display.XCreateWindow(
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
342 rootWindow,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
343 (attribs.width - cint(width)) div 2,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
344 (attribs.height - cint(height)) div 2,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
345 width,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
346 height,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
347 0,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
348 display.XDefaultDepth(screen),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
349 InputOutput,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
350 vis,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
351 CWEventMask,
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
352 addr(attrs),
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
353 )
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
354 doAssert display.XSetStandardProperties(window, title, "window", 0, nil, 0, nil) != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
355 # get an input context, to allow encoding of key-events to characters
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
356
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
357 let im = XOpenIM(display, nil, nil, nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
358 assert im != nil
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
359 let ic = im.XCreateIC(XNInputStyle, XIMPreeditNothing or XIMStatusNothing, nil)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
360 assert ic != nil
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
361
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
362 doAssert display.XMapWindow(window) != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
363
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
364 deleteMessage = display.XInternAtom("WM_DELETE_WINDOW", XBool(false))
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
365 doAssert display.XSetWMProtocols(window, addr(deleteMessage), 1) != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
366
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
367 var data = "\0".cstring
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
368 var pixmap = display.XCreateBitmapFromData(window, data, 1, 1)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
369 var color: XColor
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
370 var empty_cursor =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
371 display.XCreatePixmapCursor(pixmap, pixmap, addr(color), addr(color), 0, 0)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
372 doAssert display.XFreePixmap(pixmap) != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
373
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
374 discard display.XSync(0)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
375
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
376 # wait until window is shown
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
377 var ev: XEvent
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
378 while ev.theType != MapNotify:
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
379 discard display.XNextEvent(addr(ev))
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
380
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
381 result = NativeWindow(display: display, window: window, emptyCursor: empty_cursor, ic: ic)
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
382
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
383 proc destroyWindow*(window: NativeWindow) =
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
384 doAssert XDestroyWindow(window.display, window.window) != 0
e6bd1f553c1b add: quite a bit more wrapper
sam <sam@basx.dev>
parents: 1488
diff changeset
385