1#![cfg_attr(docsrs, feature(doc_cfg))]
14#![doc(html_root_url = "https://docs.ct2.io/bedrock/mod-peridot/")]
15
16#[cfg(feature = "VK_KHR_android_surface")]
18extern crate android;
19#[cfg(any(feature = "VK_KHR_xlib_surface", feature = "VK_EXT_acquire_xlib_display"))]
20extern crate x11;
21#[cfg(feature = "VK_KHR_xcb_surface")]
22extern crate xcb;
23
24pub use bedrock_vk::{
25 self as vk, GenericVulkanSinkStructure, GenericVulkanStructure, TypedVulkanSinkStructure, TypedVulkanStructure,
26 VkDeviceSize as DeviceSize, VkExtent2D as Extent2D, VkExtent3D as Extent3D, VkFormat as Format,
27 VkOffset2D as Offset2D, VkOffset3D as Offset3D, VkRawHandle, VkRect2D as Rect2D, VkViewport as Viewport,
28 VulkanSinkStructure, VulkanStructure,
29};
30#[cfg(feature = "Implements")]
31pub use bedrock_vk::{ResolvedFnCell, ResolverInterface, load_function_unconstrainted, load_symbol_unconstrainted};
32
33use derives::*;
34
35#[cfg(feature = "CustomResolver")]
36pub use bedrock_vk::set_resolver;
37
38pub use derives::SpecializationConstants;
39
40pub mod error;
41
42#[cfg(feature = "Implements")]
43pub mod vkfn_wrapper;
44
45macro_rules! DerefContainerWithGuardsBracketImpl {
46 (for mut $t: path { $($required: item)* }) => {
47 DerefContainerBracketImpl!(for mut $t { $($required)* });
48 GuardsImpl!(for mut $t { $($required)* });
49 };
50 (for $t: path { $($required: item)* }) => {
51 DerefContainerBracketImpl!(for $t { $($required)* });
52 GuardsImpl!(for $t { $($required)* });
53 };
54}
55macro_rules! DerefContainerBracketImpl {
56 (unsafe for mut $t: path { $($required: item)* }) => {
57 unsafe impl<'s, T> $t for &'s mut T where T: $t + ?Sized { $($required)* }
58 unsafe impl<T> $t for Box<T> where T: $t + ?Sized { $($required)* }
59 unsafe impl<T> $t for core::mem::ManuallyDrop<T> where T: $t { $($required)* }
60 };
61 (unsafe for $t: path { $($required: item)* }) => {
62 unsafe impl<'s, T> $t for &'s T where T: $t + ?Sized { $($required)* }
63 unsafe impl<T> $t for std::rc::Rc<T> where T: $t + ?Sized { $($required)* }
64 unsafe impl<T> $t for std::sync::Arc<T> where T: $t + ?Sized { $($required)* }
65
66 DerefContainerBracketImpl!(unsafe for mut $t { $($required)* });
67 };
68 (for mut $t: path { $($required: item)* }) => {
69 impl<'s, T> $t for &'s mut T where T: $t + ?Sized { $($required)* }
70 impl<T> $t for Box<T> where T: $t + ?Sized { $($required)* }
71 impl<T> $t for core::mem::ManuallyDrop<T> where T: $t { $($required)* }
72 };
73 (for $t: path { $($required: item)* }) => {
74 impl<'s, T> $t for &'s T where T: $t + ?Sized { $($required)* }
75 impl<T> $t for std::rc::Rc<T> where T: $t + ?Sized { $($required)* }
76 impl<T> $t for std::sync::Arc<T> where T: $t + ?Sized { $($required)* }
77
78 DerefContainerBracketImpl!(for mut $t { $($required)* });
79 };
80}
81macro_rules! GuardsImpl {
82 (for mut $t: path { $($required: item)* }) => {
83 impl<T> $t for std::cell::RefMut<'_, T> where T: $t + ?Sized { $($required)* }
84 impl<T> $t for std::sync::RwLockWriteGuard<'_, T> where T: $t + ?Sized { $($required)* }
85 impl<T> $t for std::sync::MutexGuard<'_, T> where T: $t + ?Sized { $($required)* }
86 impl<T> $t for parking_lot::MutexGuard<'_, T> where T: $t + ?Sized { $($required)* }
87 impl<T> $t for parking_lot::MappedMutexGuard<'_, T> where T: $t + ?Sized { $($required)* }
88 impl<T> $t for parking_lot::RwLockWriteGuard<'_, T> where T: $t + ?Sized { $($required)* }
89 impl<T> $t for parking_lot::MappedRwLockWriteGuard<'_, T> where T: $t + ?Sized { $($required)* }
90 };
91 (for $t: path { $($required: item)* }) => {
92 impl<T> $t for std::cell::Ref<'_, T> where T: $t + ?Sized { $($required)* }
93 impl<T> $t for std::sync::RwLockReadGuard<'_, T> where T: $t + ?Sized { $($required)* }
94 impl<T> $t for parking_lot::RwLockReadGuard<'_, T> where T: $t + ?Sized { $($required)* }
95 impl<T> $t for parking_lot::MappedRwLockReadGuard<'_, T> where T: $t + ?Sized { $($required)* }
96
97 GuardsImpl!(for mut $t { $($required)* });
98 };
99}
100macro_rules! ForwardFnPtr {
101 (deref $name: ident -> $t: ty) => {
102 #[inline(always)]
103 fn $name(&self) -> $t {
104 (**self).$name()
105 }
106 };
107}
108
109pub type Result<T> = core::result::Result<T, ResultCode>;
110
111#[cfg(feature = "alloc")]
112pub(crate) mod alloc;
113
114mod handle;
115use crate::error::ResultCode;
116
117pub use self::handle::*;
118
119#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
121#[must_use = "array query may finished incompletely"]
122pub struct ArrayQueryResult<T> {
123 pub result: T,
125 pub is_incomplete: bool,
128}
129impl ArrayQueryResult<()> {
130 #[inline(always)]
131 pub fn from_vk_result(r: vk::VkResult) -> Result<Self> {
132 match r {
133 vk::VK_SUCCESS => Ok(Self {
134 result: (),
135 is_incomplete: false,
136 }),
137 vk::VK_INCOMPLETE => Ok(Self {
138 result: (),
139 is_incomplete: true,
140 }),
141 e => match ResultCode(e) {
142 e if e.is_err() => Err(e),
143 e => unreachable!("unexpected result: {e:?}"),
144 },
145 }
146 }
147}
148impl<T> ArrayQueryResult<T> {
149 #[inline(always)]
150 pub fn with_result<U>(self, v: U) -> ArrayQueryResult<U> {
151 ArrayQueryResult {
152 result: v,
153 is_incomplete: self.is_incomplete,
154 }
155 }
156
157 #[inline(always)]
158 pub fn map_result<U>(self, f: impl FnOnce(T) -> U) -> ArrayQueryResult<U> {
159 ArrayQueryResult {
160 result: f(self.result),
161 is_incomplete: self.is_incomplete,
162 }
163 }
164
165 #[inline(always)]
166 pub fn assert_complete(self) -> T {
167 assert!(!self.is_incomplete, "the query was incomplete!");
168 self.result
169 }
170}
171
172#[cfg(feature = "VK_KHR_swapchain")]
173#[derive(Debug, Clone, Copy, PartialEq, Eq)]
174pub enum PresentResult {
175 Success,
177 Suboptimal,
179}
180
181#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
182pub enum TimeoutableWaitResult {
183 Success,
185 Timeout,
187}
188impl TimeoutableWaitResult {
189 pub fn from_vk_result(r: vk::VkResult) -> Self {
190 match r {
191 vk::VK_SUCCESS => Self::Success,
192 vk::VK_TIMEOUT => Self::Timeout,
193 e => unreachable!("unexpected result: {:?}", ResultCode(e)),
194 }
195 }
196}
197
198pub trait VkObject: VkHandle {
200 const TYPE: vk::VkObjectType;
201
202 #[implements("VK_EXT_debug_utils")]
209 fn set_name(&self, name: Option<&core::ffi::CStr>) -> crate::Result<()>
210 where
211 Self: DeviceChild<ConcreteDevice: InstanceChild<ConcreteInstance: InstanceDebugUtilsExtension>>,
212 Self::Handle: vk::VkRawHandle,
213 {
214 self.device()
215 .set_object_name(&DebugUtilsObjectNameInfo::new(self, name))
216 }
217}
218impl<T: VkObject + ?Sized> VkObject for &'_ T {
219 const TYPE: vk::VkObjectType = T::TYPE;
220}
221impl<T: VkObject + ?Sized> VkObject for &'_ mut T {
222 const TYPE: vk::VkObjectType = T::TYPE;
223}
224impl<T: VkObject + ?Sized> VkObject for std::rc::Rc<T> {
225 const TYPE: vk::VkObjectType = T::TYPE;
226}
227impl<T: VkObject + ?Sized> VkObject for std::sync::Arc<T> {
228 const TYPE: vk::VkObjectType = T::TYPE;
229}
230impl<T: VkObject + ?Sized> VkObject for std::cell::Ref<'_, T> {
231 const TYPE: vk::VkObjectType = T::TYPE;
232}
233impl<T: VkObject + ?Sized> VkObject for std::cell::RefMut<'_, T> {
234 const TYPE: vk::VkObjectType = T::TYPE;
235}
236impl<T: VkObject + ?Sized> VkObject for std::sync::MutexGuard<'_, T> {
237 const TYPE: vk::VkObjectType = T::TYPE;
238}
239
240pub trait AnalogNumRange<T> {
242 fn begin(&self) -> T;
243 fn end(&self) -> T;
244 fn count(&self) -> T
245 where
246 T: std::ops::Sub<T, Output = T> + Copy,
247 {
248 self.end() - self.begin()
249 }
250}
251impl<T> AnalogNumRange<T> for T
252where
253 T: std::ops::Add<u32, Output = T> + Copy,
254{
255 fn begin(&self) -> T {
256 *self
257 }
258 fn end(&self) -> T {
259 *self + 1
260 }
261}
262impl<T> AnalogNumRange<T> for std::ops::Range<T>
263where
264 T: Copy,
265{
266 fn begin(&self) -> T {
267 self.start
268 }
269 fn end(&self) -> T {
270 self.end
271 }
272}
273
274pub(crate) mod ffi_helper;
275
276mod base;
277pub use base::*;
278mod device;
279pub use device::*;
280mod sync;
281pub use sync::*;
282pub mod resources;
283pub use resources::*;
284#[macro_use]
285mod descriptor;
286pub use descriptor::*;
287mod renderpass;
288pub use self::renderpass::*;
289mod framebuffer;
290pub use framebuffer::*;
291mod shading;
292pub use shading::*;
293mod command;
294pub use command::*;
295mod debug;
296#[allow(unused_imports)]
297pub use debug::*;
298mod ext;
299pub use self::ext::*;
300mod external;
301#[allow(unused_imports)]
302pub use external::*;
303mod batching;
304pub use self::batching::*;
305mod dependency;
306#[allow(unused_imports)]
307pub use self::dependency::*;
308mod query;
309pub use self::query::*;
310
311#[cfg(feature = "VK_KHR_surface")]
312mod surface;
313#[cfg(feature = "VK_KHR_surface")]
314pub use self::surface::*;
315
316mod fmt;
317pub use self::fmt::*;