Je suis en train de déterminer comment regrouper toutes les informations dont jai besoin pour un moteur de rendu différé basé sur la physique dans un G-Buffer sans utiliser dobscène quantité de cibles de rendu.
Ce que jai jusquà présent, ce sont 4 vecteurs en 3 parties:
- Albedo / Diffuse
- Normal
- Tangente
- Position
Et 4 composants simples
- Métallisé
- Rugosité
- Hauteur
- Occlusion ambiante
Une approche naïve consiste à regrouper lun des composants individuels dans le canal alpha (quatrième) avec lun des vecteurs en 3 parties, qui est ma ligne de recherche actuelle. Cependant, étant donné que quatre cibles de rendu à virgule flottante de précision complète à 4 canaux ne sont pas petites, je comprends quil est courant dutiliser des représentations à demi-précision et encore plus petites pour être plus conscient de la mémoire.
Ce que je demande est: sur quels composants puis-je réduire la précision en toute sécurité sans perdre en qualité, et de combien?
Réponse
Tout dabord, vous navez pas du tout besoin de position dans le G-buffer. La position dun pixel peut être reconstruite à partir du tampon de profondeur , en connaissant la configuration de la caméra et la position xy de lespace écran du pixel. Vous pouvez donc vous débarrasser de tout ce tampon.
De plus, vous navez pas non plus besoin de vecteurs tangents dans le G-buffer. Ils « ne sont nécessaires que pour convertir les textures normales à partir de lespace tangent, et pour le mappage de parallaxe; ceux-ci seraient effectués pendant la passe de remplissage du G-buffer (lorsque vous avez des tangentes du maillage que vous » restituerez), et le G-buffer ne le ferait que stocker les normales dans le monde ou dans lespace de vue.
Les propriétés des matériaux comme les couleurs, la rugosité et le métal ne sont généralement que des valeurs 8 bits dans le G-buffer, car elles « proviennent de textures 8 bits. Idem pour AO.
La hauteur nest pas non plus nécessaire dans le G-buffer à moins que vous ne fassiez une sorte de fusion multipasse qui en dépend, mais si vous en avez besoin, 8 bits est probablement assez pour cela aussi.
Les normales peuvent bénéficier du stockage sous forme de valeurs 16 bits plutôt que 8 bits. Le demi-flotteur est correct, mais le virgule fixe 16 bits est encore mieux, car il vous donne une précision plus uniforme dans toutes les orientations (le demi-flotteur est plus précis près des axes et perd une certaine précision). De plus, vous pouvez les réduire de 3 composants à 2 en utilisant mappage octaédrique .
Donc, à la fin de la journée, un minimum G-buffer pourrait ressembler à:
- Couleur du matériau + métallique: RGBA8
- Espace-monde octaédrique normal + rugosité + AO: RGBA16
et cest tout! Seulement 12 octets par pixel.
Alternativement, vous pouvez utiliser un tampon RG16 pour les normales, et déplacer la rugosité + AO dans un tampon séparé de 8 bits. Cela vous donnerait un peu despace pour augmenter si vous avez besoin de plus de composants G-buffer de tailles 8 bits ou 16 bits.
Commentaires
- Aussi, la métallicité est souvent une valeur binaire, et en supposant que vous nutiliserez pas de gradients de rugosité (afin de voir limpact dune précision réduite), vous pouvez stocker la métallité et la rugosité dans un seul canal de 8 bits (1 bit pour la métallité et 7 pour la rugosité).