Search code examples
iosopengl-esmetal

OpenGLES blending code to Metal translation


I have this simple OpenGLES blending code to Metal:

 glBlendEquation(GL_FUNC_ADD);
 glBlendFunc(GL_ONE, GL_ONE);
 glEnable(GL_BLEND);

I wrote code in Metal but am confused if it is exactly does the same job. Specifically, do I need to mention alpha blending factors or no. Because I see performance of this code in Metal worse than OpenGLES which is weird. Please let me know if there is anything missing in this code.

   let renderPipelineDescriptorGreen = MTLRenderPipelineDescriptor()
    renderPipelineDescriptorGreen.vertexFunction = vertexFunctionGreen
    renderPipelineDescriptorGreen.fragmentFunction = fragmentFunctionAccumulator
    renderPipelineDescriptorGreen.colorAttachments[0].pixelFormat = .bgra8Unorm
    renderPipelineDescriptorGreen.colorAttachments[0].isBlendingEnabled = true
    renderPipelineDescriptorGreen.colorAttachments[0].rgbBlendOperation = .add
    renderPipelineDescriptorGreen.colorAttachments[0].sourceRGBBlendFactor = .one
    renderPipelineDescriptorGreen.colorAttachments[0].destinationRGBBlendFactor = .one

Solution

  • The blending configuration seems correct relative to the OpenGL code. The pipeline descriptor has default values for alpha blending that are probably fine. alphaBlendOperation defaults to .add, sourceAlphaBlendFactor defaults to .one, and destinationAlphaBlendFactor defaults to .zero.

    Of course, there's other stuff that may play a factor in performance, like the specifics of your shader functions.

    How are you measuring the performance?

    Metal apps can have higher performance than OpenGL apps, but that's not because any given single render operation is faster. The GPU hardware's performance will be the limiting factor there. Metal can achieve higher performance by eliminating overhead that OpenGL has, by giving the app more control over resource management, etc. In very simple test cases that aren't representative of real apps, these factors may not show up.