ПрограммированиеФорумГрафика

Deferred shading, stencil tes, z test проблемы

#0
15:46, 26 мая 2015

Здравствуйте. Делаю deferred shading, возникли пролемы ... ну никак не могу понять в чем проблема. Источник света точечный в виде сферы, суть пометить те пиксели которые внутри сферы, а потом фулскрин квад и осветить их. Пока фулскрин квадом ... нужно так пока разобрацо.
В общем так обстоят дела:
делаю отрисвку сцены MRT в итоге получаю 2 текстуру с цветом и нормалями, тут все ясно.

//очистка бэк буфера и стенсиля
SXEngine::Device->Clear(0, 0, D3DCLEAR_TARGET | D3DCLEAR_STENCIL,D3DCOLOR_ARGB(255,255,255,255), 0.0f, 0);

//устанавливаем стенсил тест
SXEngine::Device->SetRenderState(D3DRS_STENCILENABLE, TRUE);

//стенсил тест никада не проходит
SXEngine::Device->SetRenderState(D3DRS_STENCILFUNC, D3DCMP_NEVER);
//помечаю то что рисую
SXEngine::Device->SetRenderState(D3DRS_STENCILREF, 0x1);
  
//зэт тест и так стоит но для последовательности
SXEngine::Device->SetRenderState(D3DRS_ZENABLE, D3DZB_TRUE);
//отключаем запись в глубину
SXEngine::Device->SetRenderState(D3DRS_ZWRITEENABLE, D3DZB_FALSE);
//помечаем только ближние к камере пиксели
SXEngine::Device->SetRenderState(D3DRS_ZFUNC, D3DCMP_LESS);
SXEngine::Device->SetRenderState(D3DRS_STENCILZFAIL, D3DSTENCILOP_INCR);

//раз тест стенсиля не проходит значит помечаем то что рисуем
SXEngine::Device->SetRenderState(D3DRS_STENCILFAIL, D3DSTENCILOP_REPLACE);
//рисуем задние грани
SXEngine::Device->SetRenderState(D3DRS_CULLMODE, D3DCULL_CW);
TestLigth->Render();

а теперь помечаем те пиксели которые дальше от камеры но внутри источника света

SXEngine::Device->SetRenderState(D3DRS_ZFUNC, D3DCMP_GREATER);
SXEngine::Device->SetRenderState(D3DRS_STENCILZFAIL, D3DSTENCILOP_DECR);
SXEngine::Device->SetRenderState(D3DRS_STENCILFAIL, D3DSTENCILOP_REPLACE);
SXEngine::Device->SetRenderState(D3DRS_CULLMODE, D3DCULL_CCW);
TestLigth->Render();

теперь если значение в стунсиле равно 1 тогда эти пиксели и освещаем
отключаем запись и тест глубины и рисуем передние грани

SXEngine::Device->SetRenderState(D3DRS_STENCILFUNC, D3DCMP_EQUAL);
SXEngine::Device->SetRenderState(D3DRS_STENCILREF, 0x1);
SXEngine::Device->SetRenderState(D3DRS_STENCILFAIL, D3DSTENCILOP_ZERO);
SXEngine::Device->SetRenderState(D3DRS_STENCILZFAIL, D3DSTENCILOP_ZERO);
SXEngine::Device->SetRenderState(D3DRS_STENCILPASS, D3DSTENCILOP_KEEP);
SXEngine::Device->SetRenderState(D3DRS_CULLMODE, D3DCULL_CCW);
SXEngine::Device->SetRenderState(D3DRS_ZENABLE, D3DZB_FALSE);
SXEngine::Device->SetRenderState(D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
SXEngine::Device->SetRenderState(D3DRS_ZWRITEENABLE, D3DZB_FALSE);

В итоге ... весь экран залит одним цветом ... но если после этих операций отрисовать сцену повторно то она оказывается только в сфере, НО то что я в стенсиле помечал (тест по глубине в сферу) не работает.
Кто делал подскажите пожалуйста, никак не могу понять. Заранее спасибо!

#1
15:56, 26 мая 2015

Byurrer
> //зэт тест и так стоит но для последовательности

Что будет тут в ZBUFFER ?

#2
15:59, 26 мая 2015

innuendo в зэт буфере глубина отрисованной сцены.

#3
16:01, 26 мая 2015

Byurrer

Что заносится в ZBUFFER при очистке ?

#4
16:03, 26 мая 2015

innuendo когда рисую в мрт сцену:

SXEngine::Device->Clear(0, 0, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, D3DCOLOR_ARGB(255,255,0,0), 1.0f, 0);

перед тем кодом что в 0 посте вызываю:

SXEngine::Device->Clear(0, 0, D3DCLEAR_TARGET | D3DCLEAR_STENCIL,D3DCOLOR_ARGB(255,255,255,255), 0.0f, 0);

ну а перед отрисвкой фулскрин квад ничего.

Еще забыл сказать что сам пишу линейную глубину в пиксельном шейдере, хотя хоть сам хоть не сам результат один.

#5
17:36, 26 мая 2015

А что в D3DRS_STENCILWRITEMASK  и D3DRS_STENCILMASK ?

#6
17:37, 26 мая 2015

outcast значения по умолчанию.

#7
9:31, 28 мая 2015

Ладно, а кто-нибудь знает как можно содержимое стесиля вывести экран? ну там постпроцесс - натянуть на квад это понятно, но откуда получить можно стенсил текстуру аля сюрфейс?

#8
11:15, 28 мая 2015

Byurrer
> получить можно стенсил текстуру аля сюрфейс
Официально в D3D9 это невозможно.
Неофициально это тоже невозможно. :(
Но это возможно в OpenGL и, вполне вероятно, в новых версиях D3D.

#9
11:19, 28 мая 2015

Моласар спасибо за полный ответ.
Балин ... ересь какая-то, дурень я штоле ... нихрена не получается с етим стенсилем ...

#10
11:20, 28 мая 2015

Byurrer
> Ладно, а кто-нибудь знает как можно содержимое стесиля вывести экран?

Nsight и др

#11
15:07, 28 мая 2015

innuendo юзану еси че.
В общем то и так скисор тестом + клипом внутри пиксельного шойдера на 900 источников минимум 40 максимум 90 еси смотреть на них. Думаю более 20 одновремено попадающих будет редкость.
Причем отрисовку делал не сферой (80кадров) а фулскринквадом(90кадров). Мож здесь гдето подвох? ... хз.

ПрограммированиеФорумГрафика

Тема в архиве.