带有glTexImage2D segfaults的SDL_image加载的PNG

时间:2018-11-10 20:42:36

标签: opengl sdl-2

我认为这不是我正在加载的图像的问题。图像分辨率为256x256,因此不是2次方的幂。我看过人们使用glTexImage2D遇到的其他段错误,但该段错误似乎仍然无法消失。抱歉,代码不在C / C ++中(我也不认为这是问题所在),但它仍然应该易于理解。

let surface = sdlimage.load("image.png") # equivalent to IMG_Load call in C
if surface.isNil:
  echo "Image couldn't be loaded: ", sdl2.getError()
  quit 1

glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA)
glEnable(GL_BLEND)

var tex: cuint
glGenTextures(1, addr tex)
glBindTexture(GL_TEXTURE_2D, tex)
glPixelStorei(GL_UNPACK_ALIGNMENT, 1)
glPixelStorei(GL_UNPACK_ROW_LENGTH, surface.pitch)
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA.GLint, surface.w.GLsizei, surface.h.GLsizei, 0, GL_RGBA, GL_UNSIGNED_BYTE, surface.pixels) # segfault

更新:

由于user1118321的回答,我设法使它不发生段错误(我检查了像素格式,发现SDL使用了“索引”格式,我看到另一个用户说这是他们自己解决此问题时的问题。例如创建新曲面是正确的解决方案),但现在它在屏幕上什么也没有显示。将glClearColor设置为黑色时为黑色,而将glClearColor设置为白色时为白色。

更新的图像加载代码:

let surface = sdlimage.load("image.png")
if surface.isNil:
  echo "Image couldn't be loaded: ", sdl2.getError()
  quit 1

var w = surface.w # may need to make this the next power of two
var h = surface.h # and this
var bpp: cint
var Rmask, Gmask, Bmask, Amask: uint32
if not pixelFormatEnumToMasks(SDL_PIXELFORMAT_ABGR8888, bpp,
  Rmask, Gmask, Bmask, Amask):
  quit "pixel format enum to masks " & $sdl2.getError()

let newSurface = createRGBSurface(0, w, h, bpp,
  Rmask, Gmask, Bmask, Amask)

discard surface.setSurfaceAlphaMod(0xFF)
discard surface.setSurfaceBlendMode(BlendMode_None)

blitSurface(surface, nil, newSurface, nil)

var tex: cuint
glGenTextures(1, addr tex)
glBindTexture(GL_TEXTURE_2D, tex)
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)
glTexImage2D(GL_TEXTURE_2D, 0, 4, w.GLsizei, h.GLsizei, 0, GL_RGBA, GL_UNSIGNED_BYTE, newSurface.pixels)

图像渲染代码:

glUseProgram(shaderProgram)
glClear(GL_COLOR_BUFFER_BIT or GL_DEPTH_BUFFER_BIT)
glMatrixMode(GL_MODELVIEW)
glLoadIdentity()
glTranslatef(0.0, 0.0, -7.0)
glColor3f(1.0, 1.0, 1.0)
glBegin(GL_QUADS)
glTexCoord2i(0, 0)
glVertex3f(-0.5, -1.9, 0.0)
glTexCoord2i(1, 0)
glVertex3f(0.5, -1.9, 0.0)
glTexCoord2i(0, 1)
glVertex3f(-0.5, -1.4, 0.0)
glTexCoord2i(1, 1)
glVertex3f(0.5, -1.4, 0.0)
glEnd()

如果着色器与此有关,这是我的顶点着色器:

#version 330 core
in vec4 data;
out vec3 ourColor;
void main() {
  gl_Position = vec4(data.x, data.y, data.z, 1.0);
  ourColor = vec3(data.w, data.w, data.w);
}

还有片段着色器:

#version 330 core
precision highp float;
in vec3 ourColor;
out vec4 color;
void main() {
  color = vec4(ourColor, 1.0);
}

1 个答案:

答案 0 :(得分:1)

您应检查glGetError()以查看是否发生任何OpenGL错误。您还应该检查surface.pixelFormat,以查看图像中每个像素是否实际有4个字节。如果仅是RGB数据而不是RGBA,那么glTexImage2D()将读取图像数据的末尾,并可能由于分割错误而崩溃。