Разные шейдеры для разных объектов DirectX 11

13

Я учусь Direct3D 11, и во всех основных уроках, которые я нашел по написанию шейдеров, шейдеры Vertex и Pixel написаны так, что они преобразуют всю сцену одинаково. Учебники как рендер куб с текстурой ...

Но мне интересно, как вы различаете объекты? Что если вы хотите, например, смоделировать зеркальную поверхность на каком-либо объекте и использовать разные шейдеры для визуализации остальной части сцены? Я думаю, что большинство игр должны использовать много вершинных и пиксельных шейдеров для достижения различного вида и преобразования.

Спасибо.

jantobola
источник

Ответы:

23

Да, игровой движок, как правило, будет иметь различные шейдеры. Типичная картина:

  1. При инициализации движка и загрузке игрового мира подготовьте все шейдеры, которые вы будете использовать для рендеринга. Под «подготовкой» я подразумеваю загружать их в память, компилировать их при необходимости и выполнять все ID3D11Device::CreatePixelShaderи подобные вызовы, чтобы выделить объекты шейдера D3D и быть готовыми к работе. Храните объекты в массиве или какой-либо другой структуре данных.

    Обычно у вас будут взаимно-однозначные отношения между вершинными и пиксельными шейдерами, которые предназначены для совместной работы. Я думаю о них как об одном объекте, который я просто называю «шейдером», даже если он действительно содержит вершинный шейдер и пиксельный шейдер (и, возможно, геометрические / шейдерные / доменные шейдеры).

  2. Каждый кадр, как только вы нашли список объектов (сеток) для рендеринга, сортируйте их по шейдеру. Идея состоит в том, чтобы минимизировать количество переключений шейдеров в кадре, объединяя все объекты с данным шейдером. Это происходит потому , что переключение шейдеры является несколько дорогостоящей операцией (хотя можно , конечно , сделать это несколько сотен или тысяч раз за кадр, так что это на самом деле не что дорого).

    На самом деле, вы можете сделать еще один шаг и отсортировать сетки по шейдерам и материалам. Под «материалом» я подразумеваю комбинацию шейдера и набора текстур и параметров для него. Шейдеры обычно имеют некоторые текстуры и числовые параметры (хранящиеся в постоянных буферах), которые вводятся в них, поэтому, например, материал кирпича и асфальтовый материал могут использовать один и тот же код шейдера, только с разными текстурами.

  3. Для рисования просто зациклите шейдеры, установите каждый шейдер в ID3D11DeviceContext, установите любые параметры (постоянные буферы, текстуры и т. Д.), Затем нарисуйте объекты. В псевдокоде, включая различие между шейдерами и материалами, я упомянул:

    for each shader:
        // Set the device context to use this shader
        pContext->VSSetShader(shader.pVertexShader);
        pContext->PSSetShader(shader.pPixelShader);
    
        for each material that uses this shader:
            // Set the device context to use any constant buffers, textures, samplers,
            // etc. needed for this material
            pContext->VSSetConstantBuffers(...);
            pContext->PSSetConstantBuffers(...);
            pContext->PSSetShaderResources(...);
            pContext->PSSetSamplers(...);
    
            for each mesh that uses this material:
                // Set any constant buffers containing parameters specific to the mesh
                // (e.g. world matrix)
                pContext->VSSetConstantBuffers(...);
    
                // Set the context to use the vertex & index buffers for this mesh
                pContext->IASetInputLayout(mesh.pInputLayout);
                pContext->IASetVertexBuffers(...);
                pContext->IASetIndexBuffer(...);
                pContext->IASetPrimitiveTopology(...)
    
                // Draw it
                pContext->DrawIndexed(...)
    

Можно еще многое сказать об управлении объектами, сетками, шейдерами, макетами ввода, постоянными буферами и т. Д., Но этого должно быть достаточно для начала работы. :)

Натан Рид
источник
Вы предлагаете сортировку по шейдеру, а затем по материалу. У вас есть какие-либо достоверные данные о стоимости переключения шейдеров в сравнении с переключением материалов? Да, и для DX9 комбинация VS / PS называется «программой». Я не уверен, используют ли они эту терминологию в DX11.
Панда Пижама
1
@PandaPajama Это хороший вопрос. Нет, я не знаю или не знаю каких-либо недавних измерений реальной стоимости переключения материалов или шейдеров. Этот подход был "общей мудростью" в течение многих лет, но стоит сделать некоторые реальные измерения, чтобы увидеть, как все изменилось ... возможно, я сделаю это, если смогу найти время. :)
Натан Рид