Índice
- Introdução
- Aprendendo programação gráfica
- Não se prender a problemas triviais
- Por que Vulkan?
- Aprendendo Vulkan
- Visão geral do engine e análise de frame
- Conselhos gerais
- Bibliotecas Vulkan recomendadas
- Abstração
GfxDevice
- Tratamento de shaders
- Push constants, descriptor sets e bindless descriptors
- Padrões de pipeline
- Uso de Programmable Vertex Pulling (PVP) + Buffer Device Address (BDA)
- Bindless descriptors
- Tratamento de dados dinâmicos que precisam ser enviados a cada frame
- Destrutores, fila de deleção e limpeza
- Sincronização
- Mais notas de implementação
- Desenhar muitos sprites
- Compute skinning
- Separação entre jogo / renderizador
- Carregamento de cena e prefabs de entidade
- MSAA
- UI
- Dear ImGui e problemas de sRGB
- Outros pontos
- O que foi ganho ao migrar para Vulkan
- Trabalhos futuros
Introdução
- Este texto documenta a experiência de aprender Vulkan e escrever um pequeno engine de jogos.
- O trabalho foi feito ao longo de 3 meses sem conhecimento prévio de Vulkan.
- Foi criado um pequeno jogo 3D, e as partes reutilizáveis foram separadas em um engine.
Aprendendo programação gráfica
- Para quem está começando em programação gráfica, é melhor aprender OpenGL primeiro.
- Usar OpenGL para exibir modelos com textura na tela e aprender iluminação simples e shadow mapping é útil.
- Recursos recomendados para aprender OpenGL:
- learnopengl.com
- Livro Anton’s OpenGL 4 Tutorials
- Aulas de Thorsten Thormählen (as 6 primeiras são recomendadas)
Não se prender a problemas triviais
- É preciso tomar cuidado para não se prender a problemas triviais.
- Vale sempre se perguntar: "isso é realmente necessário?", "isso vai se tornar um gargalo?".
- Funcionalidades desnecessárias podem ser adicionadas depois.
- Comece com um jogo simples e tome cuidado para não acabar criando um engine complexo.
Por que Vulkan?
- Vulkan permite usar recursos modernos de GPU e é adequado para quem prefere tecnologias e padrões open source.
- OpenGL é suficiente para jogos pequenos, mas é difícil usar recursos modernos de GPU, e seu uso é limitado no macOS.
- WebGPU é mais fácil de aprender do que Vulkan e permite rodar jogos no navegador.
Aprendendo Vulkan
- Aprender Vulkan parecia difícil no início, mas ficou mais fácil porque a Khronos simplificou as partes complexas e forneceu bibliotecas úteis.
- Recursos recomendados para aprender Vulkan:
- vkguide
- Série de aulas de Vulkan da TU Wien
- Livro 3D Graphics Rendering Cookbook
- Livro Mastering Graphics Programming with Vulkan
Visão geral do engine e análise de frame
- O nome do engine é EDBR (Elias Daler’s Bikeshed Engine) e ele começou como um projeto de aprendizado de Vulkan.
- O engine é mais adequado para jogos pequenos baseados em fases.
- Processo de renderização de frame:
- Skinning: processamento do skinning de modelos com compute shader
- Shadow mapping: uso de textura de profundidade 4096x4096
- Geometria e shading: uso de modelo PBR
- Resolução de profundidade: tratamento manual via fragment shader
- Efeitos de pós-processamento: aplicação de depth fog, tone mapping e bloom
- UI: desenho da UI com uma única draw call
Conselhos gerais
Bibliotecas Vulkan recomendadas
- vk-bootstrap: simplifica o código de inicialização do Vulkan
- Vulkan Memory Allocator (VMA): gerencia a alocação de memória
- volk: simplifica o carregamento de funções de extensão
Abstração GfxDevice
- A classe
GfxDevice encapsula funcionalidades do Vulkan e cuida de inicialização do contexto Vulkan, criação e gerenciamento de swapchain etc.
Tratamento de shaders
- Escrever shaders usando GLSL.
- Pré-compilar os shaders na etapa de build para reduzir dependências em tempo de execução.
Push constants, descriptor sets e bindless descriptors
- No Vulkan, descriptor sets são usados para passar dados aos shaders.
- O uso de bindless descriptors e Buffer Device Address minimiza o uso de descriptor sets.
Padrões de pipeline
- As etapas de desenho são separadas usando classes de pipeline.
- Os métodos
init, cleanup e draw cuidam da inicialização, limpeza e desenho do pipeline.
Uso de Programmable Vertex Pulling (PVP) + Buffer Device Address (BDA)
- Unifica-se o tipo de vértice em um só, e o shader acessa os vértices diretamente.
- O endereço do buffer é passado usando push constants.
Bindless descriptors
- Texturas são gerenciadas de forma bindless para permitir acesso direto a partir do shader.
- O texture ID é passado por push constants para fazer o sampling.
Opinião do GN⁺
- Vulkan oferece alto desempenho e recursos modernos de GPU, mas a curva de aprendizado inicial é íngreme.
- É recomendável aprender OpenGL primeiro e depois migrar para Vulkan.
- Existem vários recursos para aprender Vulkan, e aproveitá-los facilita o estudo.
- Escrever um pequeno engine de jogos com Vulkan ajuda a entender programação gráfica em profundidade.
- É recomendável usar bibliotecas úteis para reduzir a complexidade do Vulkan.
1 comentários
Comentários do Hacker News
Resumo dos comentários do Hacker News
Efeito de uma abordagem minimalista: Está escrevendo um cliente de metaverso em Rust e enfrentando problemas complexos usando Vulkan, WGPU e Rend3. O WGPU é difícil de desenvolver porque tenta dar suporte a várias plataformas.
Vantagens do Vulkan e simplicidade do OpenGL: O Vulkan permite aproveitar ao máximo recursos avançados da GPU, mas o OpenGL é mais adequado para jogos simples em 2D ou de baixa contagem de polígonos. A indústria de jogos AAA prioriza a qualidade gráfica, mas muitos jogadores se importam mais com a jogabilidade.
Implementar apenas o necessário: Programadores juniores tendem a se apegar a ferramentas mais recentes e a "melhores práticas", mas é importante focar no conjunto mínimo de funcionalidades necessário para resolver o problema real.
Complexidade do Vulkan: Em comparação com o OpenGL, é mais difícil otimizar o desempenho no Vulkan, e ele exige muito código e trabalho de sincronização. Para hobby, OpenGL ES3 é mais prático.
Problema das camadas extras de abstração: Materiais para aprender Vulkan introduzem camadas adicionais de abstração, o que dificulta encontrar exemplos básicos de gerenciamento de memória.
Dificuldade de aprender Vulkan: O OpenGL era fácil de aprender, mas o Vulkan torna até tarefas simples mais complicadas. Aprender uma tecnologia nova consome muito tempo.
Aprendizado de Vulkan para visualização de dados científicos: Aprendeu Vulkan e escreveu um motor de visualização de dados científicos, mas levou bastante tempo para entender as muitas abstrações no processo de aprendizado.
Dificuldade no aprendizado de Vulkan: É difícil entender como usar Vulkan em um motor real. São necessários mais materiais para aprender boas abstrações e como decidir a ordem de renderização.
Apoio da comunidade de programação gráfica: Durante o desenvolvimento de um motor em Vulkan, o apoio e o feedback da comunidade foram de grande ajuda.