Çok geçişli gölgelendiriciler OpenGL'de nasıl çalışır?


13

Direct3D'de, çok geçişli gölgelendiricilerin kullanımı kolaydır, çünkü bir program içindeki geçişleri tam olarak tanımlayabilirsiniz. OpenGL'de biraz daha karmaşık görünüyor çünkü bir gölgelendirici programına istediğiniz kadar köşe, geometri ve parça gölgelendirici vermek mümkündür.

Çok geçişli gölgelendiricinin popüler bir örneği bir toon gölgelendiricisidir. Bir geçişte gerçek cel gölgeleme efekti yapılır, diğeri anahat oluşturur. "Cel.vert" ve "anahat.vert" olmak üzere iki köşe gölgelendiricim ve "cel.frag" ve "anahat.frag" (HLSL'de yaptığınız gibi) iki parça gölgelendiricim varsa, nasıl yapabilirim? tam toon gölgelendirici oluşturmak için onları birleştirmek?

Bunun için bir geometri gölgelendiricisinin kullanılabileceğini söylemenizi istemiyorum çünkü sadece çok geçişli GLSL gölgelendiricilerinin arkasındaki teoriyi bilmek istiyorum;)


"Direct3D'de, çok geçişli gölgelendiricilerin kullanımı kolaydır, çünkü bir program içindeki geçişleri tam olarak tanımlayabilirsiniz." Hayır yapamazsın. Geçişleri FX dosyasında tanımlayabilirsiniz, ancak bu bir HLSL gölgelendiricisi ile aynı değildir.
Nicol Bolas

Yanıtlar:


11

Çoklu geçişin arkasında "teori" yoktur. "Çok geçişli gölgelendirici" yoktur. Çok geçişli çok basittir: nesneyi bir programla çizersiniz. Ardından nesneyi farklı bir programla çizersiniz.

Bu ekstra geçişleri gizlemek için FX dosyaları gibi D3DX öğelerini kullanabilirsiniz. Ama hala bu şekilde çalışıyorlar. OpenGL'nin bunun için bir saklanma yeri yok.


1

Nesneyi hücre gölgelendiricisi ile işleyin ve ardından anahat gölgelendiricisi ile yeniden oluşturun.


1
Yani iki farklı gölgelendirici programı yapmalıyım? O zaman neden bir gölgelendirici programını istediğim kadar köşe / geometri / parça gölgelendirici verebilirim? Bunu tek bir programla yapmanın bir yolu olmalı.
jmegaffin

1
Birden çok köşe (vb.) Gölgelendiricisi vermiyorsunuz. Yalnızca bir ana işlev vardır, bu nedenle birden fazla giriş noktanız yoktur. Bir program yapmak için birbirine bağlı birden fazla dosyaya sahip olabilmeniz C programına çok benzer. Bu dosyaları farklı programlar arasında paylaşabilirsiniz, böylece kodu çoğaltmanız gerekmez, ancak her dosya kendi başına bir program değildir.
Chewy Gumball

1
Bu şekilde gidebilir, bir gölgelendirici çifti (tepe + parça) ile bir kez renderleyin ve daha sonra başka bir çiftle yeniden renderlayın (veya aynı tepe noktası gölgelendiricisini + başka bir parça gölgelendiriciyi kullanın). Bazen bir tampona dönüştürür ve son sonuca 'karıştırmak' için başka bir gölgelendirici kullanırsınız.
Valmond

1

OpenGL 4.0'da tekdüze alt rutinler vardır . Bunlar, çalışma zamanında çok az ek yük ile değiştirilebilen işlevleri tanımlamanıza olanak tanır. Böylece her geçiş için 1 fonksiyon yapabilirsiniz. Ayrıca her gölgelendirici türü için 1 işlev.

Burada bir öğretici var .

Eski OpenGL sürümleri için en iyi seçenek ya bir grup farklı gölgelendiriciye sahip olmak ve aralarında takas yapmaktır. Aksi takdirde, açmak veya kapatmak için 0.0 veya 1.0 olan bir tekdüze ile çarptığınız değerleri birlikte ekleyebilirsiniz. Aksi takdirde ifadeler kullanılabiliyorsa, ancak OpenGL her yürütme / geçişte olası tüm sonuçları yürütecekse koşullu olduğundan, çok ağır olmadıklarından emin olun.


0

GLSL hakkında çok şey bilen bazı insanlar var, bu yüzden umarım rekoru düzleştirirler, ancak gördüklerime dayanarak, parça gölgelendiricinizde böyle bir şey yapabilmeniz gerekir (sözde kod, ben Gerçek GLSL'yi daha iyi bilen insanlara bırakacağım):

out vec4 fragment_color
vec4 final_color
final_color = flat_color
If this fragment is in shadow
    final_color = shadow_color
If this fragment is an edge
    final_color = edge_color
If this fragment is a highlight
    final_color = highlight_color
fragment_color = final_color

S'yi ifbu şekilde kullanarak , çoklu geçişler gibi bir şey elde edersiniz. bu mantıklı mı?

Düzenleme: Ayrıca, umarım SO bu soru bazı yanlış anlama gidermek yardımcı olur.


2
GLSL'nin, eğer dallar her geçişte etkin olmasa bile tüm ifadeleri yürüteceğini unutmamak önemlidir. Görünüşe göre sadece her şeyi hesaplamak ve tüm renkleri birlikte eklemek, ancak bunları etkinleştirmek veya devre dışı bırakmak için değerleri 1.0 veya 0.0 ile çarpmak daha hızlıdır.
David

1
@ DavidC.Bishop: Bu doğru değil. En azından doğru olduğu garanti edilmez . Derleyici, gerçek bir dalın daha hızlı olup olmadığına veya "her şeyi hesapla ve sonra sırala" yaklaşımının daha hızlı olduğuna karar verecektir.
Nicol Bolas

1
Bir kenara, @ DavidC.Bishop tarafından atıfta bulunulan davranış gölgelendiricilere ve GPU'ya pek özgü değildir. Test edilen değer henüz mevcut değilse, normal programları yürüten modern CPU'lar spekülatif olarak dallardan en az birini yürütür. Eğer yanlış oldukları ortaya çıkarsa, geri dönüp tekrar yaparlar. Bu, ortalama olarak büyük bir hızlanma sağlar.
ipeet
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.