Iphone OpenGL ES 2.0 for iOS-对GLDraweElements的多个调用导致EXC\u BAD\u访问

Iphone OpenGL ES 2.0 for iOS-对GLDraweElements的多个调用导致EXC\u BAD\u访问,iphone,ios,opengl-es,opengl-es-2.0,3d,Iphone,Ios,Opengl Es,Opengl Es 2.0,3d,几年前,我为OpenGLES1.1和iPhone编写了一个小型Cocoa/Obj-C游戏框架。这是在iOS3.x流行的时候。我的OpenGLES1.1/IOS3.x实现都很好。随着时间的推移,我们现在看到了iOS5.1、OpenGLES2.0、ARC、块和其他东西。我决定是时候把这个项目转移到更多的。。。现代标准 编辑:自己解决了其中一个问题,那就是为什么它会在模拟器上崩溃。有点-我现在可以画更小的模型,但更大的模型(如测试警车)仍然会导致EXC_BAD_访问-即使这是唯一一次调用GLDrawe

几年前,我为OpenGLES1.1和iPhone编写了一个小型Cocoa/Obj-C游戏框架。这是在iOS3.x流行的时候。我的OpenGLES1.1/IOS3.x实现都很好。随着时间的推移,我们现在看到了iOS5.1、OpenGLES2.0、ARC、块和其他东西。我决定是时候把这个项目转移到更多的。。。现代标准

编辑:自己解决了其中一个问题,那就是为什么它会在模拟器上崩溃。有点-我现在可以画更小的模型,但更大的模型(如测试警车)仍然会导致EXC_BAD_访问-即使这是唯一一次调用GLDrawerElements。我还能够修复在模拟器上绘制多个网格的问题——不过,我不知道这是否会在设备上运行到明天早上。(我的5.0测试设备是我朋友的iPhone,不要)。所以我想主要的问题是,为什么较大的模型会导致模拟器上的EXC_坏访问

原文如下 然而,在将其升级到5.0的过程中,我遇到了一些OpenGL ES 2.0错误——具体来说,其中两个错误,尽管它们可能是相关的。第一个很简单——如果我尝试在设备(运行5.0.1的iPhone 4S)上渲染我的模型,它会显示出来,但是如果我尝试在模拟器(运行5.0的iPhone模拟器)上显示它,它会在GLD元素上抛出EXC_BAD_访问。第二,也很简单。我无法绘制多个网格。当我将模型绘制为一个大组(一个顶点数组/索引数组组合)时,它绘制得很好-但当我将模型绘制为多个部分(例如,对抽屉元素的多次调用)时,它失败,并显示一个大黑屏-黑色不是来自正在绘制的模型(我已经验证了这一点,如下所述)

在更详细的部分之前总结一下,试图在模拟器上渲染我的模型会崩溃

警告:对于小网格,这一切都很好。即使在模拟器上,我也可以一遍又一遍地绘制静态声明的小立方体。当我说静态声明时,我指的是绑定并加载到顶点缓冲区的硬编码结构常量数组,以及绑定并加载到索引数组的结构常量数组

注意:我说的“模型”是指一个整体模型,可能由多个顶点和索引缓冲区组成。在代码中,这意味着模型仅包含一组网格或模型组。网格或模型组是模型的子单元,例如模型的一个相邻部分,具有一个顶点数组和一个索引数组,并存储这两个数组的长度。在我使用的模型中,车身是一个网格,车窗是另一个网格,车灯是第三个网格。他们一起组成了这个模型

我使用的模型是一辆警车,有几千个顶点和面,被分成多个部分(车身、灯光、窗户等)-车身大约有3000个面,窗户大约100个,灯光稍微少一点

以下是一些需要知道的事情:

  • 我的模型加载正常。我用两种方法验证了这一点- 打印出模型顶点并手动检查它们,以及 分别显示每个模型组,如图2所示。我会发布图片,但“声誉限制”,这是我的第一个问题,我不能。我还从头开始重新构建了两次模型加载器,没有任何更改,因此我知道顶点和索引缓冲区的顺序/格式正确

  • 当我将模型作为单个模型组(即一个顶点)加载时 缓冲区/索引缓冲区)正确显示整个模型。当我 将模型作为多个模型组加载,并显示任何给定的 单独显示模型组时,它将正确显示。当我试着画画的时候 多个模型组(对GLDraweElements的多个调用)大 出现黑屏

  • 黑屏不是因为正在绘制模型。我 通过更改片段着色器以绘制每个像素来验证这一点 红色无论如何。我总是将颜色缓冲区清除为中灰色(显然,我也会清除深度缓冲区),但尝试绘制多个网格/模型组会导致黑屏。我们知道它并不是简单地遮蔽视图的模型,因为它是黑色而不是红色。这发生在设备上,我不知道模拟器上会发生什么,因为我无法让它绘制

  • 我的模型不会在模拟器中绘制。它既不会绘制为单个网格/模型组,也不会绘制为多个网格/模型组。应用程序正确加载,但是 尝试绘制网格/模型组会导致在 元素。回溯的相关部分包括:

     thread #1: tid = 0x1f03, 0x10b002b5, stop reason = EXC_BAD_ACCESS (code=1, address=0x94fd020)
        frame #0: 0x10b002b5
        frame #1: 0x09744392 GLEngine`gleDrawArraysOrElements_ExecCore + 883
        frame #2: 0x09742a9b GLEngine`glDrawElements_ES2Exec + 505
        frame #3: 0x00f43c3c OpenGLES`glDrawElements + 64
        frame #4: 0x0001cb11 MochaARC`-[Mesh draw] + 177 at Mesh.m:81
    
    编辑:它始终能够绘制较小的动态创建模型(~100个面),但整个模型的3000个面除外

  • 我能够让它渲染一个更小、更简单但仍然动态加载的模型,该模型由192个面/576个顶点组成。我可以将其显示为单个顶点和索引缓冲区,也可以将其拆分为多个部分并渲染为多个较小的顶点和索引缓冲区。试图在模拟器中绘制单个网格模型导致EXC_BAD_访问仍被抛出,但仅在第一帧。如果我强迫它继续,它会显示一个非常糟糕的模型,然后每一帧之后,它都会显示出100%的完美,就像它应该显示的那样

  • 我的着色器没有错误。当我使用一个小的、静态声明的顶点缓冲区时,它们可以正确编译和显示。然而,为了完整性,我将在底部发布它们


  • 我的代码如下:

    渲染循环:

    glClearColor(0.65f,0.65f,0.65f,1.0f);
    glClear(GL_颜色_缓冲_位| GL_深度_缓冲_位);
    //muShader是我编写的着色器处理程序的一个子类,它跟踪活动着色器
    //并处理属性/制服
    //[穆沙德
    
    attribute highp vec4 position;
    attribute lowp vec3 uv;
    
    varying lowp vec3 fragmentUV;
    
    uniform highp mat4 modelViewProjection;
    uniform lowp sampler2D texture;
    
    void main()
    {
        fragmentUV = uv;
    
        gl_Position = modelViewProjection * position;
    }
    
    varying lowp vec3 fragmentUV;
    
    uniform highp mat4 modelViewProjection;
    uniform lowp sampler2D texture;
    
    void main()
    {
        gl_FragColor = texture2D(texture,fragmentUV.xy);
        //used below instead to test the aforementioned black screen by setting
        //every pixel of the model being drawn to red
        //the screen stayed black, so the model wasn't covering the whole screen or anything
        //gl_FragColor = vec4(1,0,0,1);
    }