Skip to content

Commit 32b8ae9

Browse files
committed
Textured Meshes
1 parent 6112adc commit 32b8ae9

9 files changed

Lines changed: 73 additions & 19 deletions

File tree

.gitmodules

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,3 +10,6 @@
1010
[submodule "libs/glm"]
1111
path = libs/glm
1212
url = https://github.com/g-truc/glm.git
13+
[submodule "libs/glTF-Sample-Models"]
14+
path = libs/glTF-Sample-Models
15+
url = https://github.com/KhronosGroup/glTF-Sample-Models.git

libs/glTF-Sample-Models

Submodule glTF-Sample-Models added at 8e9a5a6

shaders/model_frag.glsl

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,15 @@
11
#version 450 core
22

33
layout(location = 0) in vec3 in_normal;
4+
layout(location = 1) in vec2 in_texcoord;
5+
6+
layout(set = 0, binding = 1) uniform sampler2D in_albedoSampledTexture;
47

58
layout(location = 0) out vec4 out_color;
69

710
void main() {
11+
vec4 texSample = texture(in_albedoSampledTexture, in_texcoord);
812
vec3 normal = normalize(in_normal);
9-
out_color = vec4(normal * 0.5 + 0.5, 1.0);
13+
//out_color = vec4(normal * 0.5 + 0.5, 1.0);
14+
out_color = texSample;
1015
}

shaders/model_frag.spv

164 Bytes
Binary file not shown.

shaders/model_vert.glsl

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,15 +2,18 @@
22

33
layout(location = 0) in vec3 in_position;
44
layout(location = 1) in vec3 in_normal;
5+
layout(location = 2) in vec2 in_texcoord;
56

67
layout(set = 0, binding = 0) uniform transform {
78
mat4 modelViewProj;
89
} u_transforms;
910

1011
layout(location = 0) out vec3 out_normal;
12+
layout(location = 1) out vec2 out_texcoord;
1113

1214
void main() {
1315
mat4 modelViewProj = u_transforms.modelViewProj;
1416
gl_Position = modelViewProj * vec4(in_position, 1.0);
1517
out_normal = in_normal;
18+
out_texcoord = in_texcoord;
1619
}

shaders/model_vert.spv

192 Bytes
Binary file not shown.

src/main.cpp

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,9 @@ void initApplication(SDL_Window* window) {
161161

162162
recreateRenderPass();
163163

164+
//model = createModel(context, "../data/models/monkey.glb");
165+
model = createModel(context, "../libs/glTF-Sample-Models/2.0/BoomBox/glTF-Binary/BoomBox.glb");
166+
164167
{
165168
VkSamplerCreateInfo createInfo = {VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO};
166169
createInfo.magFilter = VK_FILTER_NEAREST;
@@ -227,6 +230,7 @@ void initApplication(SDL_Window* window) {
227230
{
228231
VkDescriptorPoolSize poolSizes[] = {
229232
{VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, FRAMES_IN_FLIGHT},
233+
{VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, FRAMES_IN_FLIGHT},
230234
};
231235
VkDescriptorPoolCreateInfo createInfo = {VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO};
232236
createInfo.maxSets = FRAMES_IN_FLIGHT;
@@ -240,6 +244,7 @@ void initApplication(SDL_Window* window) {
240244
{
241245
VkDescriptorSetLayoutBinding bindings[] = {
242246
{0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, 0},
247+
{1, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler},
243248
};
244249
VkDescriptorSetLayoutCreateInfo createInfo = {VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO};
245250
createInfo.bindingCount = ARRAY_COUNT(bindings);
@@ -254,13 +259,20 @@ void initApplication(SDL_Window* window) {
254259
VKA(vkAllocateDescriptorSets(context->device, &allocateInfo, &modelDescriptorSets[i]));
255260

256261
VkDescriptorBufferInfo bufferInfo = {modelUniformBuffers[i].buffer, 0, sizeof(glm::mat4)};
257-
VkWriteDescriptorSet descriptorWrites[1];
262+
VkDescriptorImageInfo imageInfo = {sampler, model.albedoTexture.view, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL};
263+
VkWriteDescriptorSet descriptorWrites[2];
258264
descriptorWrites[0] = {VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET};
259265
descriptorWrites[0].dstSet = modelDescriptorSets[i];
260266
descriptorWrites[0].dstBinding = 0;
261267
descriptorWrites[0].descriptorCount = 1;
262268
descriptorWrites[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
263269
descriptorWrites[0].pBufferInfo = &bufferInfo;
270+
descriptorWrites[1] = {VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET};
271+
descriptorWrites[1].dstSet = modelDescriptorSets[i];
272+
descriptorWrites[1].dstBinding = 1;
273+
descriptorWrites[1].descriptorCount = 1;
274+
descriptorWrites[1].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
275+
descriptorWrites[1].pImageInfo = &imageInfo;
264276
VK(vkUpdateDescriptorSets(context->device, ARRAY_COUNT(descriptorWrites), descriptorWrites, 0, 0));
265277
}
266278
}
@@ -292,19 +304,23 @@ void initApplication(SDL_Window* window) {
292304
vertexAttributeDescriptions, ARRAY_COUNT(vertexAttributeDescriptions), &vertexInputBinding, 1, &spriteDescriptorLayout, 0);
293305

294306

295-
VkVertexInputAttributeDescription modelAttributeDescriptions[2] = {};
307+
VkVertexInputAttributeDescription modelAttributeDescriptions[3] = {};
296308
modelAttributeDescriptions[0].binding = 0;
297309
modelAttributeDescriptions[0].location = 0;
298310
modelAttributeDescriptions[0].format = VK_FORMAT_R32G32B32_SFLOAT;
299311
modelAttributeDescriptions[0].offset = 0;
300312
modelAttributeDescriptions[1].binding = 0;
301313
modelAttributeDescriptions[1].location = 1;
302314
modelAttributeDescriptions[1].format = VK_FORMAT_R32G32B32_SFLOAT;
303-
modelAttributeDescriptions[1].offset = 0;
315+
modelAttributeDescriptions[1].offset = sizeof(float) * 3;
316+
modelAttributeDescriptions[2].binding = 0;
317+
modelAttributeDescriptions[2].location = 2;
318+
modelAttributeDescriptions[2].format = VK_FORMAT_R32G32_SFLOAT;
319+
modelAttributeDescriptions[2].offset = sizeof(float) * 6;
304320
VkVertexInputBindingDescription modelInputBinding = {};
305321
modelInputBinding.binding = 0;
306322
modelInputBinding.inputRate = VK_VERTEX_INPUT_RATE_VERTEX;
307-
modelInputBinding.stride = sizeof(float) * 6;
323+
modelInputBinding.stride = sizeof(float) * 8;
308324
modelPipeline = createPipeline(context, "../shaders/model_vert.spv", "../shaders/model_frag.spv", renderPass, swapchain.width, swapchain.height,
309325
modelAttributeDescriptions, ARRAY_COUNT(modelAttributeDescriptions), &modelInputBinding, 1, &modelDescriptorSetLayout, 0);
310326

@@ -339,8 +355,6 @@ void initApplication(SDL_Window* window) {
339355
createBuffer(context, &spriteIndexBuffer, sizeof(indexData), VK_BUFFER_USAGE_INDEX_BUFFER_BIT | VK_BUFFER_USAGE_TRANSFER_DST_BIT, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);
340356
uploadDataToBuffer(context, &spriteIndexBuffer, indexData, sizeof(indexData));
341357

342-
model = createModel(context, "../data/models/monkey.glb");
343-
344358
{ // Init camera
345359
camera.cameraPosition = glm::vec3(0.0f);
346360
camera.cameraDirection = glm::vec3(0.0f, 0.0f, 1.0f);
@@ -449,7 +463,7 @@ void renderApplication() {
449463
vkCmdDrawIndexed(commandBuffer, ARRAY_COUNT(indexData), 1, 0, 0, 0);
450464
#else
451465
glm::mat4 translationMatrix = glm::translate(glm::mat4(1.0f), glm::vec3(0.0f, 0.0f, 3.0f));
452-
glm::mat4 scaleMatrix = glm::scale(glm::mat4(1.0f), glm::vec3(1.0f));
466+
glm::mat4 scaleMatrix = glm::scale(glm::mat4(1.0f), glm::vec3(100.0f));
453467
glm::mat4 rotationMatrix = glm::rotate(glm::mat4(1.0f), -time, glm::vec3(0.0f, 1.0f, 0.0f));
454468
glm::mat4 modelMatrix = translationMatrix * scaleMatrix * rotationMatrix;
455469

src/model.cpp

Lines changed: 38 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@
33
#define CGLTF_IMPLEMENTATION
44
#include <cgltf/cgltf.h>
55

6+
#include <stb/stb_image.h>
7+
68
// Stride in bytes. Element size in bytes
79
void fillBuffer(uint32_t inputStride, void* inputData, uint32_t outputStride, void* outputData, uint32_t numElements, uint32_t elementSize) {
810
uint8_t* output = (uint8_t*)outputData;
@@ -27,7 +29,6 @@ Model createModel(VulkanContext* context, const char* filename) {
2729
assert(data->meshes_count == 1);
2830
assert(data->meshes[0].primitives_count == 1);
2931
assert(data->meshes[0].primitives[0].attributes_count > 0);
30-
assert(data->meshes[0].primitives[0].attributes[0].type == cgltf_attribute_type_position);
3132
assert(data->meshes[0].primitives[0].indices->component_type == cgltf_component_type_r_16u);
3233
assert(data->meshes[0].primitives[0].indices->stride == sizeof(uint16_t));
3334

@@ -42,30 +43,55 @@ Model createModel(VulkanContext* context, const char* filename) {
4243

4344

4445
// Vertices
46+
uint64_t outputStride = sizeof(float)*8;
4547
uint64_t numVertices = data->meshes[0].primitives[0].attributes->data->count;
46-
uint64_t vertexDataSize = sizeof(float) * 6 * numVertices;
48+
uint64_t vertexDataSize = outputStride * numVertices;
4749
uint8_t* vertexData = new uint8_t[vertexDataSize];
4850
for(uint64_t i = 0; i < data->meshes[0].primitives[0].attributes_count; ++i) {
4951
cgltf_attribute* attribute = data->meshes[0].primitives[0].attributes + i;
52+
bufferBase = (uint8_t*)attribute->data->buffer_view->buffer->data;
53+
uint64_t inputStride = attribute->data->stride;
5054
if(attribute->type == cgltf_attribute_type_position) {
51-
assert(attribute->data->stride == sizeof(float)*3);
52-
bufferBase = (uint8_t*)attribute->data->buffer_view->buffer->data;
53-
uint64_t positionDataSize = attribute->data->buffer_view->size;
5455
void* positionData = bufferBase + attribute->data->buffer_view->offset;
55-
fillBuffer(sizeof(float)*3, positionData, sizeof(float) * 6, vertexData, numVertices, sizeof(float)*3);
56-
} else if(attribute->type == cgltf_attribute_type_normal) {
57-
assert(attribute->data->stride == sizeof(float)*3);
58-
bufferBase = (uint8_t*)attribute->data->buffer_view->buffer->data;
59-
uint64_t normalDataSize = attribute->data->buffer_view->size;
56+
fillBuffer(inputStride, positionData, outputStride, vertexData, numVertices, sizeof(float)*3);
57+
} else if(attribute->type == cgltf_attribute_type_normal) {
6058
void* normalData = bufferBase + attribute->data->buffer_view->offset;
61-
fillBuffer(sizeof(float)*3, normalData, sizeof(float) * 6, vertexData+(sizeof(float)*3), numVertices, sizeof(float)*3);
59+
fillBuffer(inputStride, normalData, outputStride, vertexData+(sizeof(float)*3), numVertices, sizeof(float)*3);
60+
} else if(attribute->type == cgltf_attribute_type_texcoord) {
61+
void* texcoordData = bufferBase + attribute->data->buffer_view->offset;
62+
fillBuffer(inputStride, texcoordData, outputStride, vertexData+(sizeof(float)*6), numVertices, sizeof(float)*2);
6263
}
6364
}
6465
createBuffer(context, &result.vertexBuffer, vertexDataSize, VK_BUFFER_USAGE_VERTEX_BUFFER_BIT | VK_BUFFER_USAGE_TRANSFER_DST_BIT, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);
6566
uploadDataToBuffer(context, &result.vertexBuffer, vertexData, vertexDataSize);
6667
delete[] vertexData;
68+
69+
// Material
70+
assert(data->materials_count == 1);
71+
cgltf_material* material = &data->materials[0];
72+
assert(material->has_pbr_metallic_roughness);
73+
cgltf_texture_view albedoTextureView = material->pbr_metallic_roughness.base_color_texture;
74+
assert(!albedoTextureView.has_transform);
75+
assert(albedoTextureView.texcoord == 0);
76+
assert(albedoTextureView.texture);
77+
cgltf_texture* albedoTexture = albedoTextureView.texture;
78+
79+
// Load texture
80+
cgltf_buffer_view* bufferView = albedoTexture->image->buffer_view;
81+
assert(bufferView->size < INT32_MAX);
82+
int bpp, width, height;
83+
uint8_t* textureData = stbi_load_from_memory((stbi_uc*) bufferView->buffer->data, (int)bufferView->size, &width, &height, &bpp, 4);
84+
assert(textureData);
85+
bpp = 4;
86+
createImage(context, &result.albedoTexture, width, height, VK_FORMAT_R8G8B8A8_SRGB, VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT);
87+
uploadDataToImage(context, &result.albedoTexture, textureData, width * height * bpp, width, height, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, VK_ACCESS_SHADER_READ_BIT);
88+
stbi_image_free(textureData);
89+
} else {
90+
LOG_ERROR("Could not load additional model buffers");
6791
}
6892
cgltf_free(data);
93+
} else {
94+
LOG_ERROR("Could not load model file");
6995
}
7096

7197
return result;
@@ -74,5 +100,6 @@ Model createModel(VulkanContext* context, const char* filename) {
74100
void destroyModel(VulkanContext* context, Model* model) {
75101
destroyBuffer(context, &model->vertexBuffer);
76102
destroyBuffer(context, &model->indexBuffer);
103+
destroyImage(context, &model->albedoTexture);
77104
*model = {};
78105
}

src/model.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ struct Model {
44
VulkanBuffer vertexBuffer;
55
VulkanBuffer indexBuffer;
66
uint64_t numIndices;
7+
VulkanImage albedoTexture;
78
};
89

910
Model createModel(VulkanContext* context, const char* filename);

0 commit comments

Comments
 (0)