Похоже, что эта функция очень плохо документирована. В туториалах по шейдерам геометрии в DirectX SDK нет примера использования CreateGeometryShaderWithStreamOutput и нигде нет потоков, объясняющих основы этого. В msdn написано, какие функции использовать для его создания , но не как и для чего он используется. Есть ли кто-нибудь, кто успешно его использовал, можете ли вы поделиться небольшим примером или ссылкой на учебник для него? Для чего он используется и хорош ли он с точки зрения производительности? Насколько я понял , он используется для отбраковки усеченной пирамиды на основе графического процессора?
Как вы используете Geometry Shader с выходным потоком?
Ответы (1)
Вы можете найти 2 примера в DirectX SDK (в разделе DirectX 10)
- ТрубыGS
- ЧастицыGS
Вы также можете ознакомиться с примерами NVidia: http://developer.download.nvidia.com/SDK/10/direct3d/samples.html
Rain и Metaballs используют поток
Все эти семплы на dx10, но их довольно легко портировать на dx11 (всего несколько битов для замены).
Для него существует несколько применений (неполный список):
- Динамические частицы
- Предварительная обработка модели (скининг, смещение, тесселяция). Таким образом, вы можете применить смещение к своей модели один раз, а затем повторно привязать смещенную модель к нескольким проходам (карта теней/материал...)
- Экспорт модели: сгенерируйте некоторую геометрию в шейдере, верните поток вывода обратно в процессор и экспортируйте в виде 3D-модели.
Если вы хотите использовать необработанный конвейер вместо потокового вывода, вам необходимо выполнить следующее (это сводка из Microsoft Stream Output документация)
FX Framework делает то же самое под капотом.
Ваш шейдер Geometry должен быть создан с помощью CreateGeometryShaderWithStreamOutput
вместо CreateGeometryShader
Вам необходимо установить D3D11_SO_DECLARATION_ENTRY, чтобы соответствовать макету вывода вашего геометрического шейдера (это работает так же, как входной ассемблер)
Затем убедитесь, что ваш буфер создан с доступом к потоковому выводу:
D3D11_BUFFER_DESC bufferDesc;
bufferDesc.BindFlags = otherBindFlags | D3D11_BIND_STREAM_OUTPUT;
bufferDesc.Usage = D3D11_USAGE_DEFAULT;
bufferDesc.CPUAccessFlags = 0;
Обратите внимание, что другие флаги BindFlags не могут быть D3D11_BIND_UNORDERED_ACCESS в то же время (хотя Shader View и Raw Views разрешены).
Наконец, прежде чем выполнять отрисовку, назначьте буфер вывода потока с помощью SOSetTargets:
UINT offset[1] = 0;
ID3D11Buffer* m_pBuffer (your buffer created before)
deviceContext->SOSetTargets( 1, &m_pBuffer, offset );
Как только вы закончите с вызовом отрисовки, не забудьте очистить, используя:
UINT offset[1] = 0;
ID3D11Buffer* pNullBuffer = 0;
deviceContext->SOSetTargets( 1, &pNullBuffer, offset );