Load operations (#105)

* load ops: design + implementation (all backends)

* Animometer/glTFViewer: use just one subpass per frame
This commit is contained in:
Kai Ninomiya
2017-08-11 14:36:20 -07:00
committed by GitHub
parent 3d1154786f
commit b985431c82
18 changed files with 380 additions and 102 deletions

View File

@@ -138,17 +138,15 @@ void frame() {
size_t i = 0;
std::vector<nxt::CommandBuffer> commands(50);
for (size_t j = 0; j < 50; j++) {
nxt::CommandBuffer commands;
{
nxt::CommandBufferBuilder builder = device.CreateCommandBufferBuilder()
.BeginRenderPass(renderpass, framebuffer)
.BeginRenderSubpass()
.SetRenderPipeline(pipeline)
.Clone();
for (int k = 0; k < 200; k++) {
for (int k = 0; k < 10000; k++) {
shaderData[i].time = f / 60.0f;
builder.SetPushConstants(nxt::ShaderStageBit::Vertex, 0, 6, reinterpret_cast<uint32_t*>(&shaderData[i]))
.DrawArrays(3, 1, 0, 0);
@@ -157,10 +155,10 @@ void frame() {
builder.EndRenderSubpass();
builder.EndRenderPass();
commands[j] = builder.GetResult();
commands = builder.GetResult();
}
queue.Submit(50, commands.data());
queue.Submit(1, &commands);
backbuffer.TransitionUsage(nxt::TextureUsageBit::Present);
swapchain.Present(backbuffer);
DoFlush();

View File

@@ -126,7 +126,9 @@ nxt::RenderPass CreateDefaultRenderPass(const nxt::Device& device) {
return device.CreateRenderPassBuilder()
.SetAttachmentCount(2)
.AttachmentSetFormat(0, nxt::TextureFormat::R8G8B8A8Unorm)
.AttachmentSetColorLoadOp(0, nxt::LoadOp::Clear)
.AttachmentSetFormat(1, nxt::TextureFormat::D32FloatS8Uint)
.AttachmentSetDepthStencilLoadOps(1, nxt::LoadOp::Clear, nxt::LoadOp::Clear)
.SetSubpassCount(1)
.SubpassSetColorAttachment(0, 0, 0)
.SubpassSetDepthStencilAttachment(0, 1)

View File

@@ -80,7 +80,6 @@ nxt::Queue queue;
nxt::SwapChain swapchain;
nxt::TextureView depthStencilView;
nxt::RenderPass renderpass;
nxt::Framebuffer lastFramebuffer;
nxt::Buffer defaultBuffer;
std::map<std::string, nxt::Buffer> buffers;
@@ -478,8 +477,7 @@ namespace {
// Drawing
namespace {
void drawMesh(const tinygltf::Mesh& iMesh, const glm::mat4& model) {
nxt::CommandBufferBuilder cmd = device.CreateCommandBufferBuilder();
void drawMesh(nxt::CommandBufferBuilder& cmd, const tinygltf::Mesh& iMesh, const glm::mat4& model) {
for (const auto& iPrim : iMesh.primitives) {
if (iPrim.mode != gl::Triangles) {
fprintf(stderr, "unsupported primitive mode %d\n", iPrim.mode);
@@ -507,8 +505,6 @@ namespace {
material.uniformBuffer.SetSubData(0,
sizeof(u_transform_block) / sizeof(uint32_t),
reinterpret_cast<const uint32_t*>(&transforms));
cmd.BeginRenderPass(renderpass, lastFramebuffer);
cmd.BeginRenderSubpass();
cmd.SetRenderPipeline(material.pipeline);
cmd.TransitionBufferUsage(material.uniformBuffer, nxt::BufferUsageBit::Uniform);
cmd.SetBindGroup(0, material.bindGroup0);
@@ -551,14 +547,10 @@ namespace {
// DrawArrays
cmd.DrawArrays(vertexCount, 1, 0, 0);
}
cmd.EndRenderSubpass();
cmd.EndRenderPass();
}
auto commands = cmd.GetResult();
queue.Submit(1, &commands);
}
void drawNode(const tinygltf::Node& node, const glm::mat4& parent = glm::mat4()) {
void drawNode(nxt::CommandBufferBuilder& cmd, const tinygltf::Node& node, const glm::mat4& parent = glm::mat4()) {
glm::mat4 model;
if (node.matrix.size() == 16) {
model = glm::make_mat4(node.matrix.data());
@@ -579,22 +571,33 @@ namespace {
model = parent * model;
for (const auto& meshID : node.meshes) {
drawMesh(scene.meshes[meshID], model);
drawMesh(cmd, scene.meshes[meshID], model);
}
for (const auto& child : node.children) {
drawNode(scene.nodes.at(child), model);
drawNode(cmd, scene.nodes.at(child), model);
}
}
void frame() {
nxt::Texture backbuffer;
GetNextFramebuffer(device, renderpass, swapchain, depthStencilView, &backbuffer, &lastFramebuffer);
nxt::Framebuffer framebuffer;
GetNextFramebuffer(device, renderpass, swapchain, depthStencilView, &backbuffer, &framebuffer);
framebuffer.AttachmentSetClearColor(0, 0.3f, 0.4f, 0.5f, 1);
const auto& defaultSceneNodes = scene.scenes.at(scene.defaultScene);
nxt::CommandBufferBuilder cmd = device.CreateCommandBufferBuilder()
.BeginRenderPass(renderpass, framebuffer)
.BeginRenderSubpass()
.Clone();
for (const auto& n : defaultSceneNodes) {
const auto& node = scene.nodes.at(n);
drawNode(node);
drawNode(cmd, node);
}
auto commands = cmd.EndRenderSubpass()
.EndRenderPass()
.GetResult();
queue.Submit(1, &commands);
backbuffer.TransitionUsage(nxt::TextureUsageBit::Present);
swapchain.Present(backbuffer);
DoFlush();