Răsfoiți Sursa

Add rlSetBlendFactorsSeparate and custom blend mode modification checks (#2741)

凌溢狐 2 ani în urmă
părinte
comite
2d88958d35
1 a modificat fișierele cu 45 adăugiri și 2 ștergeri
  1. 45 2
      src/rlgl.h

+ 45 - 2
src/rlgl.h

@@ -413,7 +413,8 @@ typedef enum {
     RL_BLEND_ADD_COLORS,                // Blend textures adding colors (alternative)
     RL_BLEND_SUBTRACT_COLORS,           // Blend textures subtracting colors (alternative)
     RL_BLEND_ALPHA_PREMULTIPLY,         // Blend premultiplied textures considering alpha
-    RL_BLEND_CUSTOM                     // Blend textures using custom src/dst factors (use rlSetBlendFactors())
+    RL_BLEND_CUSTOM,                    // Blend textures using custom src/dst factors (use rlSetBlendFactors())
+    RL_BLEND_CUSTOM_SEPARATE            // Blend textures using custom src/dst factors (use rlSetBlendFactorsSeparate())
 } rlBlendMode;
 
 // Shader location point type
@@ -595,6 +596,7 @@ RLAPI void rlClearScreenBuffers(void);                  // Clear used screen buf
 RLAPI void rlCheckErrors(void);                         // Check and log OpenGL error codes
 RLAPI void rlSetBlendMode(int mode);                    // Set blending mode
 RLAPI void rlSetBlendFactors(int glSrcFactor, int glDstFactor, int glEquation); // Set blending mode factor and equation (using OpenGL factors)
+RLAPI void rlSetBlendFactorsSeparate(int srgb, int drgb, int salpha, int dalpha, int ergb, int ealpha); // Set blending mode factors and equations separately (using OpenGL factors)
 
 //------------------------------------------------------------------------------------
 // Functions Declaration - rlgl functionality
@@ -930,6 +932,13 @@ typedef struct rlglData {
         int glBlendSrcFactor;               // Blending source factor
         int glBlendDstFactor;               // Blending destination factor
         int glBlendEquation;                // Blending equation
+        int glBlendSrcFactorRGB;            // Blending source RGB factor
+        int glBlendDestFactorRGB;           // Blending destination RGB factor
+        int glBlendSrcFactorAlpha;          // Blending source alpha factor
+        int glBlendDestFactorAlpha;         // Blending destination alpha factor
+        int glBlendEquationRGB;             // Blending equation for RGB
+        int glBlendEquationAlpha;           // Blending equation for alpha
+        bool glCustomBlendModeModified;     // Custom blending factor and equation modification status
 
         int framebufferWidth;               // Current framebuffer width
         int framebufferHeight;              // Current framebuffer height
@@ -1788,7 +1797,7 @@ void rlCheckErrors()
 void rlSetBlendMode(int mode)
 {
 #if defined(GRAPHICS_API_OPENGL_33) || defined(GRAPHICS_API_OPENGL_ES2)
-    if (RLGL.State.currentBlendMode != mode)
+    if (RLGL.State.currentBlendMode != mode || ((mode == RL_BLEND_CUSTOM || mode == RL_BLEND_CUSTOM_SEPARATE) && RLGL.State.glCustomBlendModeModified))
     {
         rlDrawRenderBatch(RLGL.currentBatch);
 
@@ -1805,21 +1814,52 @@ void rlSetBlendMode(int mode)
                 // NOTE: Using GL blend src/dst factors and GL equation configured with rlSetBlendFactors()
                 glBlendFunc(RLGL.State.glBlendSrcFactor, RLGL.State.glBlendDstFactor); glBlendEquation(RLGL.State.glBlendEquation);
             } break;
+            case RL_BLEND_CUSTOM_SEPARATE:
+            {
+                // NOTE: Using GL blend src/dst factors and GL equation configured with rlSetBlendFactorsSeparate()
+                glBlendFuncSeparate(RLGL.State.glBlendSrcFactorRGB, RLGL.State.glBlendDestFactorRGB, RLGL.State.glBlendSrcFactorAlpha, RLGL.State.glBlendDestFactorAlpha);
+                glBlendEquationSeparate(RLGL.State.glBlendEquationRGB, RLGL.State.glBlendEquationAlpha);
+                break;
+            }
             default: break;
         }
 
         RLGL.State.currentBlendMode = mode;
+        RLGL.State.glCustomBlendModeModified = false;
     }
 #endif
 }
 
+// Set blending mode factor and equation used by glBlendFuncSeparate and glBlendEquationSeparate
+void rlSetBlendFactorsSeparate(int srcRGB, int dstRGB, int srcAlpha, int dstAlpha, int modeRGB, int modeAlpha) {
+#if defined(GRAPHICS_API_OPENGL_33) || defined(GRAPHICS_API_OPENGL_ES2)
+    if (RLGL.State.glBlendSrcFactorRGB == srcRGB
+        && RLGL.State.glBlendDestFactorRGB == dstRGB
+        && RLGL.State.glBlendSrcFactorAlpha == srcAlpha
+        && RLGL.State.glBlendDestFactorAlpha == destAlpha
+        && RLGL.State.glBlendEquationRGB == modeRGB
+        && RLGL.State.glBlendEquationAlpha == modeAlpha) return;
+    RLGL.State.glBlendSrcFactorRGB = srcRGB;
+    RLGL.State.glBlendDestFactorRGB = destRGB;
+    RLGL.State.glBlendSrcFactorAlpha = srcAlpha;
+    RLGL.State.glBlendDestFactorAlpha = dstAlpha;
+    RLGL.State.glBlendEquationRGB = modeRGB;
+    RLGL.State.glBlendEquationAlpha = modeAlpha;
+    RLGL.State.glCustomBlendModeModified = true;
+#endif
+}
+
 // Set blending mode factor and equation
 void rlSetBlendFactors(int glSrcFactor, int glDstFactor, int glEquation)
 {
 #if defined(GRAPHICS_API_OPENGL_33) || defined(GRAPHICS_API_OPENGL_ES2)
+    if (RLGL.State.glBlendSrcFactor == glSrcFactor
+        && RLGL.State.glBlendDstFactor == glDstFactor
+        && RLGL.State.glBlendEquation == glEquation) return;
     RLGL.State.glBlendSrcFactor = glSrcFactor;
     RLGL.State.glBlendDstFactor = glDstFactor;
     RLGL.State.glBlendEquation = glEquation;
+    RLGL.State.glCustomBlendModeModified = true;
 #endif
 }
 
@@ -1969,6 +2009,9 @@ void rlglInit(int width, int height)
     //----------------------------------------------------------
 #endif
 
+    // Init state: custom blend factor and equation modification flag
+    RLGL.State.glCustomBlendModeModified = false;
+
     // Init state: Color/Depth buffers clear
     glClearColor(0.0f, 0.0f, 0.0f, 1.0f);                   // Set clear color (black)
     glClearDepth(1.0f);                                     // Set clear depth value (default)