source: opengl-game/vulkan-buffer.hpp@ 8dcbf62

feature/imgui-sdl
Last change on this file since 8dcbf62 was 8dcbf62, checked in by Dmitry Portnoy <dportnoy@…>, 3 years ago

Add some functionality to VulkanBuffer, and modify VulkanGame::addObject() to call VulkanBuffer::add()

  • Property mode set to 100644
File size: 3.8 KB
Line 
1#ifndef _VULKAN_BUFFER_H
2#define _VULKAN_BUFFER_H
3
4/*
5* This class is intended to be used with Storage Buffers and Uniform Buffers.
6*/
7
8template<class T>
9class VulkanBuffer {
10
11 public:
12
13 // TODO: Make these private (maybe make a getter for numObjects)
14 // Externally, they are only used in resizeBufferSet
15 size_t capacity;
16 size_t numObjects;
17
18 VulkanBuffer();
19 VulkanBuffer(size_t capacity, size_t minOffsetAlignment);
20 ~VulkanBuffer();
21
22 VulkanBuffer<T>& operator=(const VulkanBuffer<T>& other);
23
24 void add(T obj);
25
26 // TODO: Add a resize function
27
28 private:
29
30 size_t alignment;
31
32 T* srcData; // TODO: Rename this to something else probably and rename rawData to data
33 vector<T>* vData;
34
35 // Remember that this is a pointer to the mapped video memory
36 // Maybe rename it to mappedData or something to make that clearer
37 void* rawData;
38};
39
40// Currently, for SSBOs, I store the per-object values (usually just the model matrix), on each object, so they
41// are not in their own array and therefore cannot be pushed to the GPU as one block. The updates must happen
42// separately per object.
43
44// Since Sascha WIllems' dynamic UBO example works the same way (iirc), I can implement dynamic UBOs like that as well
45// for now. Would be nice to plan for potentially storing the ubo data on the CPU in a contiguous block in the future,
46// assuming that would make updates easier. Keep in mind that this only makes sense if all or most of the objects
47// in the ubo get updated every frame.
48
49// ============================= TODO: Also, check when it makes sense to have a staging buffer for copying data to the GPU
50// and see if I actually need to use it everywhere I currently am. I think this is mentioned in Sascha WIllems dubo example
51// or some other Vulkan website I recently bookmarked
52
53template<class T>
54VulkanBuffer<T>::VulkanBuffer()
55 : alignment(0)
56 , capacity(0)
57 , numObjects(0)
58 , srcData(nullptr)
59 , rawData(nullptr)
60 , vData(nullptr) {
61}
62
63template<class T>
64VulkanBuffer<T>::VulkanBuffer(size_t capacity, size_t minOffsetAlignment)
65 : alignment(sizeof(T))
66 , capacity(capacity)
67 , numObjects(0)
68 , srcData(nullptr)
69 , rawData(nullptr)
70 , vData(nullptr) {
71 if (minOffsetAlignment > 0) {
72 alignment = (alignment + minOffsetAlignment - 1) & ~(minOffsetAlignment - 1);
73 }
74
75 srcData = (T*)malloc(capacity * alignment);
76}
77
78template<class T>
79VulkanBuffer<T>::~VulkanBuffer() {
80 if (srcData != nullptr) {
81 free(srcData);
82 }
83}
84
85template<class T>
86VulkanBuffer<T>& VulkanBuffer<T>::operator=(const VulkanBuffer<T>& other) {
87 if (this == &other) {
88 return *this;
89 }
90
91 /*
92 // assume *this manages a reusable resource, such as a heap-allocated buffer mArray
93 if (size != other.size) { // resource in *this cannot be reused
94 delete[] mArray; // release resource in *this
95 mArray = nullptr;
96 size = 0; // preserve invariants in case next line throws
97 mArray = new int[other.size]; // allocate resource in *this
98 size = other.size;
99 }
100 */
101
102 if (srcData != nullptr) {
103 free(srcData);
104 srcData = nullptr;
105 }
106
107 alignment = other.alignment;
108 capacity = other.capacity;
109
110 srcData = (T*)malloc(capacity * alignment);
111 // TODO: Check for failure
112
113 memcpy(srcData, other.srcData, capacity * alignment);
114
115 return *this;
116}
117
118template<class T>
119void VulkanBuffer<T>::add(T obj) {
120 numObjects++;
121}
122
123#endif // _VULKAN_BUFFER_H
Note: See TracBrowser for help on using the repository browser.