Як приховати контур обробленої сітки, коли / де сітка прихована


10

Я працюю над налаштуванням активного контуру в моєму 3d-двигуні, ефектом виділення для вибраних 3d-персонажів або декорацій на екрані. Після роботи з буфером трафарету та отримання незадовільних результатів (проблеми з увігнутими формами, товщиною контуру через відстань від камери та невідповідності між моїм робочим столом та ноутбуком) я перейшов до виявлення країв та вибірки буфера кадру та отримав контур Я досить задоволений.

Однак я не в змозі приховати контур, коли вибрана сітка знаходиться за іншою сіткою. Це має сенс, враховуючи мій процес, оскільки я просто надаю контур 2d шейдера з буфера кадру після рендерингу решти сцени.

Нижче наведено два екрани моїх результатів. Перший - це "хороший" контур, другий - там, де контур бачиться через сітку, яка блокує контурне джерело.

введіть тут опис зображення

Процес візуалізації працює так: 1) Намалюйте лише альфа виділеної сітки, фіксуючи чорний силует в буфері кадру (framebuffer1).

2) Передайте текстуру від framebuffer1 до другого шейдера, який виконує виявлення ребер. Захопіть край у framebuffer2.

3) Візуалізуйте всю сцену.

4) Візуалізуйте текстуру з framebuffer2 поверх сцени.

У мене є кілька ідей про те, як досягти і сподіваюся отримати зворотній зв'язок щодо їх дійсності або про більш прості або кращі методи.

По-перше, я подумав передати всю сцену в буфер кадру та зберегти видимий силует виділеної сітки в альфа-каналі (усе біле, крім того, де видно виділену сітку). Тоді я б здійснив виявлення ребер на альфа-каналі, відтворив буфер кадру сцени, а потім візуалізував край зверху. Отримавши щось подібне:

результат

Для цього я подумав встановити визначення лише під час проходу виділеного виділеного об'єкта, який би намалював усе чорне в альфа для будь-яких видимих ​​пікселів.

Моя друга ідея - використовувати поточний процес візуалізації, викладений вище, але також зберігати координати X, Y і Z у каналах R, G і B framebuffer1 під час надання силуету вибраної сітки. Виявлення країв виконуватиметься та зберігатиметься у framebuffer2, але я передавав би значення RGB / XYZ від країв альфа до силуету. Тоді під час візуалізації сцени я би перевіряв, чи є координата в межах краю, що зберігається у framebuffer2. Якщо так, то я би перевірив глибину поточного фрагмента, щоб визначити, чи знаходиться він перед або за координатами, витягнутими з каналів RGB (перетвореним у простір камери). Якщо фрагмент знаходиться перед координатами глибини, фрагмент буде виведений нормально. Якщо фрагмент знаходиться позаду, він буде відображатися як суцільний контурний колір.

Я використовую LibGDX для цього проекту і хотів би підтримувати WebGL та OpenGL ES, тому жодне з рішень, що стосуються шейдерів геометрії або нових функцій GLSL, мені не доступні. Якщо хтось міг би прокоментувати запропоновані мною підходи або запропонувати щось краще, я дуже вдячний.


Подивився на ваше репо. Ви коли-небудь знаходили прийнятне рішення?
iKlsR

Відповіді:


0

Я б перетворив усю сцену в буфер трафарету з потрібним окресленим об'єктом, щоб встановити трохи, а що-небудь інше відкинути / видалити.

Тоді позбудьтесь виявлення ребер, вам це не потрібно, натомість ви можете просто збільшити розмір буфера вгору. Тож кожен об’єкт просто трохи росте.

Звідси у вас буфер трафарету може мати потрібний контур. Вся справа в тому, щоб переконатися, що інші об'єкти, які ви надаєте, відключають біти у буфері трафарету.


2
Дякую за відповідь. Чи не вдалося б цей метод зіткнутися з подібними проблемами з товщиною / контурами та увігнутими формами, якщо масштабування проводиться в 3d? Або проблеми з переміщенням, якщо це було зроблено в 2d, а окреслений об'єкт не знаходиться в мертвій частині екрана?
nils

0

1) в буферному об'єкті кадру ви можете запустити лаплаціанський шейдер в GPU для отримання контуру.

2) вам потрібно використовувати буфер остаточної глибини, коли ви малюєте ваш об'єкт у ФБО, таким чином ви намалюєте лише видиму частину вашого об'єкта у ФБО, а лаплаціан контурить лише видиму частину.


Привіт, дякую за відповідь. Я вже роблю це, щоб досягти наміченого контуру. Я не думаю, що ти заслуговуєш на те, щоб відповісти на цю відповідь.
nils

0

Я сподіваюся, що я можу зробити це зрозумілим, але в основному вам потрібно зробити трафарет обох об’єктів так, як ніби вони обидва вибрані, а тоді зберігати лише ті ділянки в обмежувальному полі предмета, який ви насправді хочете виділити.

Тому в основному ви робите один буфер трафарету з обох об'єктів, вибраних (або всі об'єкти, що закривають об'єкт, насправді ..., але я б не турбувався про ці випадки, якщо його насправді не виникає багато - якщо це окклюдовані люди не збираються очікувати ця допомога), потім і це за допомогою трафарету обмежувальної коробки для вашого об'єкта.

Це має отримати ефект, який ви шукаєте.

Крім того, ви можете просто залишити «поганий» результат, і я не думаю, що більшість людей буде надто піклуватися, хоча це залежить від ваших даних / гри та особливо розміру об’єктів.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.