Включить прозрачность в 3D — pyopengl

У меня есть GLViewWidget, куда я добавляю разные объекты (GLMeshItem), устанавливая эти свойства, чтобы включить прозрачность:

        opt = {
            GL_DEPTH_TEST: True,
            'glBlendFunc': (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA),
            }
        obj.setGLOptions(opt)

Это почти работает в следующем смысле: если у меня есть два объекта obj1 и obj2, и я добавлю их в виджет в таком порядке, я увижу obj2 позади obj1, но не наоборот.

Я пробовал добавлять объекты в другом порядке, но явно увижу obj1 за obj2, а не наоборот. Как я могу заставить это работать для всех объектов безразлично?


person charles    schedule 17.12.2015    source источник
comment
Вам нужно будет отсортировать их в обратном порядке и нарисовать в правильном порядке.   -  person BDL    schedule 17.12.2015
comment
Но, как я уже сказал, оба объекта прозрачны, поэтому я хочу, чтобы они вели себя одинаково, то есть obj2 отображался за obj1, а obj1 отображался за obj2, в зависимости от точки, с которой я смотрю.   -  person charles    schedule 17.12.2015
comment
Единственный способ (кроме Order Independent Transparency) — сортировать объекты в каждом кадре в соответствии с их текущим положением и рисовать их сзади на передний план.   -  person BDL    schedule 17.12.2015


Ответы (1)


Тестирование глубины и прозрачность не слишком хорошо работают вместе.

Предположим, мы нарисовали ваш полупрозрачный объект obj1. Это также запишет его глубину в буфер глубины. Теперь предположим, что мы хотим нарисовать второй объект, obj2, который имеет большую глубину. Мы ожидаем, что увидим от obj2 до obj1, поскольку obj1 полупрозрачно.

Однако, поскольку глубина obj2 больше, перекрывающиеся пиксели не будут отображаться, так как тест глубины не пройден, поэтому мы увидим только те части obj2, которые не перекрываются obj1.

Тестирование глубины не принимает во внимание прозрачность. Так что для того, чтобы это тоже заработало, как сказал BDL в комментариях, вам придется вручную сортировать объекты и рисовать их в правильном порядке.

person Reigertje    schedule 17.12.2015
comment
Отключение проверки глубины не требуется. Правильное смешивание может быть достигнуто только тогда, когда объекты рисуются сзади наперед, что означает, что проверка глубины больше не является проблемой. Даже если сортировка не выполняется, необходимо включить как минимум тестирование глубины и отключить запись глубины. В противном случае прозрачные объекты не были бы скрыты непрозрачными. - person BDL; 17.12.2015
comment
Вы правы, отключать его не обязательно. Отредактировал это. Я хотел сказать, что, вероятно, больше нет необходимости включать его. - person Reigertje; 17.12.2015
comment
Итак, предположим, что я сначала рисую obj1 в декартовых координатах (0,0,0), затем я рисую obj2 в декартовых координатах (2,0,0). Если я посмотрю на сцену с осью x, направленной на экран, я увижу obj1 за прозрачным obj2, и это правильно. Но если я поверну сцену и посмотрю на нее с осью x, указывающей внутрь экрана, должен ли я снова отсортировать объекты, чтобы obj2 отображался за прозрачным obj1? - person charles; 18.12.2015
comment
Да. obj2 имеет большую глубину, поэтому, если вы сначала нарисуете obj1 во втором сценарии, obj2 не будет нарисовано из-за проверки глубины. Я предлагаю вам прочитать, как работает глубинное тестирование, и это также может содержать полезную информацию: opengl.org/wiki/ Прозрачность_Сортировка - person Reigertje; 18.12.2015