BGE: Add alpha to coverage render mode.
authorPorteries Tristan <republicthunderbolt9@gmail.com>
Fri, 3 Jul 2015 17:03:29 +0000 (19:03 +0200)
committerPorteries Tristan <republicthunderbolt9@gmail.com>
Fri, 3 Jul 2015 17:03:29 +0000 (19:03 +0200)
This patch add a new option for transparency meshes : Alpha to coverage, in the game setting panel in material.
The alpha to coverage request a multisample, the best is 8x but 4x and 2x can also give nice render.

4x alpha clip : http://www.pasteall.org/pic/show.php?id=89464
4x alpha to coverage : http://www.pasteall.org/pic/show.php?id=89463

Reviewers: moguri, kupoman, campbellbarton, psy-fi

Reviewed By: psy-fi

Subscribers: lordloki, rdb

Projects: #game_engine

Differential Revision: https://developer.blender.org/D1354

source/blender/gpu/GPU_material.h
source/blender/gpu/intern/gpu_draw.c
source/blender/makesdna/DNA_material_types.h
source/blender/makesrna/intern/rna_material.c

index ee6e02547e7c605dd8af5046a24e86f4f1987f03..b8a7fca1380047686edb4de48c157e30731c4671 100644 (file)
@@ -108,7 +108,8 @@ typedef enum GPUBlendMode {
        GPU_BLEND_ADD = 1,
        GPU_BLEND_ALPHA = 2,
        GPU_BLEND_CLIP = 4,
-       GPU_BLEND_ALPHA_SORT = 8
+       GPU_BLEND_ALPHA_SORT = 8,
+       GPU_BLEND_ALPHA_TO_COVERAGE = 16
 } GPUBlendMode;
 
 typedef struct GPUNodeStack {
index a24067fc3812393506ddafb3463d0f47408540af..2186f20d1730c0e10b2479ca8a84549328948309 100644 (file)
@@ -409,15 +409,18 @@ static void gpu_set_alpha_blend(GPUBlendMode alphablend)
        if (alphablend == GPU_BLEND_SOLID) {
                glDisable(GL_BLEND);
                glDisable(GL_ALPHA_TEST);
+               glDisable(GL_SAMPLE_ALPHA_TO_COVERAGE);
                glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
        }
        else if (alphablend == GPU_BLEND_ADD) {
                glEnable(GL_BLEND);
                glBlendFunc(GL_ONE, GL_ONE);
                glDisable(GL_ALPHA_TEST);
+               glDisable(GL_SAMPLE_ALPHA_TO_COVERAGE);
        }
        else if (ELEM(alphablend, GPU_BLEND_ALPHA, GPU_BLEND_ALPHA_SORT)) {
                glEnable(GL_BLEND);
+               glDisable(GL_SAMPLE_ALPHA_TO_COVERAGE);
 
                /* for OpenGL render we use the alpha channel, this makes alpha blend correct */
                if (GLEW_VERSION_1_4)
@@ -438,10 +441,16 @@ static void gpu_set_alpha_blend(GPUBlendMode alphablend)
                }
        }
        else if (alphablend == GPU_BLEND_CLIP) {
-               glDisable(GL_BLEND); 
+               glDisable(GL_BLEND);
+               glDisable(GL_SAMPLE_ALPHA_TO_COVERAGE);
                glEnable(GL_ALPHA_TEST);
                glAlphaFunc(GL_GREATER, 0.5f);
        }
+       else if (alphablend == GPU_BLEND_ALPHA_TO_COVERAGE) {
+               glEnable(GL_ALPHA_TEST);
+               glAlphaFunc(GL_GREATER, U.glalphaclip);
+               glEnable(GL_SAMPLE_ALPHA_TO_COVERAGE);
+       }
 }
 
 static void gpu_verify_alpha_blend(int alphablend)
index c3270430a3a007f833270bba9463e7debd53385e..8790f7366004f6d457474b3f32605094c666ea0d 100644 (file)
@@ -210,6 +210,7 @@ typedef struct Material {
 #define        GEMAT_ALPHA             2 /* GPU_BLEND_ALPHA */
 #define GEMAT_CLIP             4 /* GPU_BLEND_CLIP */
 #define        GEMAT_ALPHA_SORT        8 /* GPU_BLEND_ALPHA_SORT */
+#define        GEMAT_ALPHA_TO_COVERAGE 16 /* GPU_BLEND_ALPHA_TO_COVERAGE */
 
 // Game Options - flag
 #define GEMAT_BACKCULL                 16 /* KX_BACKCULL */
index 874e861f75f68a5bfe107214263f8015412b526a..38ff701510a0d7df5988f4a7da73a08207cc1ddc 100644 (file)
@@ -837,6 +837,8 @@ static void rna_def_material_gamesettings(BlenderRNA *brna)
                              "Render polygon transparent, depending on alpha channel of the texture"},
                {GEMAT_ALPHA_SORT, "ALPHA_SORT", 0, "Alpha Sort",
                                   "Sort faces for correct alpha drawing (slow, use Alpha Clip instead when possible)"},
+               {GEMAT_ALPHA_TO_COVERAGE, "ALPHA_TO_COVERAGE", 0, "Alpha Antialiasing",
+                               "Use textures alpha as anti-aliasing mask, requires multi-sample OpenGL display"},
                {0, NULL, 0, NULL, NULL}
        };