ios - 使用 GLKit 在 OpenGL 中的 glBlendFunc 透明度

标签 ios objective-c opengl-es opengl-es-2.0 glkit

我将 GLKit 用于 iPad 应用程序。使用此代码,我设置了混合:

glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

它工作正常,但是当我尝试获取屏幕截图时,混合模式似乎错误。我使用 GLKit 的快照还是 glReadPixels 都没有关系。

这是我在使用该应用程序时得到的:
enter image description here

这是屏幕截图:
enter image description here

在制作屏幕截图之前,我是否必须更改混合模式或其他东西?如果是这样,对什么?

最佳答案

您遇到的问题很可能在于如何从 RGBA 数据生成图像。要解决这个问题,您需要在创建 CGImage 时跳过 alpha channel 。与 kCGImageAlphaNoneSkipLast或者首先在缓冲区中具有正确的 alpha 值。

解释发生了什么。您的 GL 缓冲区由 RGBA 值组成,但仅使用 RGB 部分来呈现它,但是当您创建图像时,您也使用 alpha channel ,因此存在差异。它是如何实现的非常简单,让我们在屏幕中间的某个地方取一个像素并查看它的事件:

  • 您将像素清除为您想要的任何颜色
  • 您使用从纹理接收到的纯色覆盖像素(所有 4 个 channel RGBA),例如 (.8, .8, .8, 1.0)
  • 你用一些较小的 alpha 值在该像素上绘制颜色并尝试混合它,例如 (.4, .4, .4, .25) .您的混合函数说将源颜色与源 alpha 相乘,将目标颜色与 1 - 源 alpha 相乘。这导致 (.4, .4, .4, .25)*.25 + (.8, .8, .8, 1.0)*.75 = (.7, .7, .7, .76)

  • 现在结果(.7, .7, .7, .76)显示得很好,因为您的缓冲区仅显示 RGB 部分,导致看到 (.7, .7, .7, 1.0)但是当您使用所有 4 个组件来创建图像时,您还使用了 .76 alpha 值,该值进一步用于混合图像本身。因此,您需要在某些时候跳过 alpha 部分。

    还有另一种方法:正如您在您的情况下看到的,实际上根本不需要将 alpha 值存储到渲染缓冲区,因为您从不使用它,在您的混合函数中,您只使用源 alpha。因此,您可以使用 glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_FALSE) 禁用它。 ,这也意味着您需要将 alpha 值清除为 1.0 ( glClearColor(x,x,x,1.0) )

    关于ios - 使用 GLKit 在 OpenGL 中的 glBlendFunc 透明度,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16788785/

    相关文章:

    iphone - 如何像 uitableviewcell 一样重用/回收自定义元素?

    android - OpenGL Android 应用程序适用于大多数手机,但纹理在 Xoom 上显示为白色

    ios - 在 iOS 上运行小型周期性高优先级后台任务

    ios - 无法从 iOS 7 中的 App Store Receipt 获取 original_application_version

    ios - Swift 中的 IBM Silverpop 推送集成

    android - glOrtho OpenGL es 2.0 变体如何修复空白屏幕?

    android - 何时在 Android 游戏的方法中同步方法或使用同步块(synchronized block)?

    iphone - 哪种调整 UIImage 大小的方法更好,为什么?

    android - CSS android 和 iOS 问题

    objective-c - 子类化 UIButton 但无法访问我的属性