Opengl трафарет буфер установлен, когда не прозрачный

Я пытался настроить свой буфер трафарета так, чтобы при включении он устанавливался, когда нарисованный пиксель не является прозрачным (таким образом создавая карту пикселей, с которой может столкнуться свет). Что я сделал, это:

    glClearStencil(0); //clear stencil
    glStencilFunc(GL_EQUAL, 0xFF, 0x000000FF); //only where alpha (mask : 0x000000FF) is 0xFF (opaque)
    glStencilOp(GL_INCR, GL_KEEP, GL_KEEP); //increment if passes (if it is opaque)

    render(); //withing this method I sometimes disable the whole thing to draw the floor, for example

Затем я использую следующий код для проверки:

    /* TURN OFF STENCIL */
    glEnable(GL_STENCIL_TEST); //re-enable
    glStencilFunc(GL_EQUAL, 0, 1); //if the test is equal to 1
    glStencilOp(GL_KEEP, GL_KEEP, GL_KEEP); //do not change stencil buffer

    ImageInfo.drawColorSquare(0, 0, Configurations.SCREEN_WIDTH, Configurations.GAME_HEIGHT, Color.BLUE); //drwa blue square

    glDisable(GL_STENCIL_TEST); //disable

Однако есть две проблемы:

  1. Кажется, он не игнорирует прозрачные пиксели, как следует;
  2. Если регион перекрывается с другим, то он меняет местами - например, он устанавливает один, затем другой регион рисуется в той же области, и он снова сбрасывает его в 0.

Я не знаю, почему это происходит. Наверное, что-то не так с моей маской - наверное, я не был абсолютно уверен, сколько пикселей использует OpneGL в Color Buffer. Кроме того, GL_INCR должен составлять максимум и не возвращаться, согласно документации. Поскольку размер моего буфера трафарета составляет один бит, он должен быть равен единице, попытаться снова увеличить его, потерпеть неудачу и сохранить один (вместо сброса).

2 ответа

Решение

Тест трафарета не зависит от того, что происходит в буфере цвета. настройка glStencilFunc( http://www.opengl.org/sdk/docs/man/xhtml/glStencilFunc.xml) вы можете указать, как Stencil Test взаимодействует с тем, что уже хранится в буфере трафарета.
настройка glStencilOp ( http://www.opengl.org/sdk/docs/man/xhtml/glStencilOp.xml) дает вам возможность использовать результаты теста глубины для выполнения теста трафарета. Хороший учебник, который объясняет тест трафарета и очень поучительный алгоритм на его основе, можно найти здесь http://ogldev.atspace.co.uk/www/tutorial37/tutorial37.html

Трафаретный буфер обычно представляет собой 8-битный буфер, который резервирует небольшую часть памяти, обычно используемую для буфера глубины, и используется для расширенного отклонения фрагментов; такие вещи, как маскировка произвольных форм, а не использование прямоугольных ножничных ящиков. Он не имеет ничего общего с вашим цветовым буфером, и чтобы убедиться, что фрагменты с определенным альфа-значением не влияют на пиксели на экране, вы должны использовать то, что называется альфа-тестом.

В ядре OpenGL 3 альфа-тест с фиксированной функцией больше не поддерживается, поэтому вам придется реализовать его в фрагментном шейдере, а затем discard если оно не соответствует вашим условиям.

Другие вопросы по тегам