D 프로그래밍 언어로 SDL과 OpenGL을 사용하여 2D 게임을 작성하고 있습니다. 지금은 단순히 텍스처 매핑 된 쿼드를 화면에 렌더링하려고 시도합니다. 문제는 전체 텍스처 매핑 부분이 제대로 작동하지 않는 것입니다. 분명히로드하는 텍스처에도 (0이 아닌 텍스처 번호가 지정되고, glGetError가 0이 아닌 값을 반환하지는 않지만), 쿼드는 glColor에서 마지막으로 설정된 색상으로 렌더링되어 텍스처를 완전히 무시합니다.OpenGL 텍스처 맵핑이 고집스럽게 작동하지 않습니다.
this question을 포함하여 텍스처 매핑이 실패하는 일반적인 이유를 찾지 못했습니다. 로드되는 이미지 파일은 유효한 2의 거듭 제곱 크기 인 64x64입니다.
거의 완전히 C 스타일의 SDL 및 OpenGL 호출이기 때문에 두려워하지 마십시오.
SDL 초기화 코드 :
if (SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1) == -1 ||
SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 0) == -1)
throw new Exception("An OpenGL attribute could not be set!");
uint videoFlags = SDL_OPENGL | SDL_HWSURFACE | SDL_ANYFORMAT;
if (threadsPerCPU() > 1)
videoFlags |= SDL_ASYNCBLIT;
SDL_Surface* screen = SDL_SetVideoMode(800, 600, 32, videoFlags);
if (screen == null)
throw new Exception("SDL_SetVideoMode failed!");
OpenGL을 초기화 코드 :
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0., 800, 600, 0., 0., 1.);
glMatrixMode(GL_MODELVIEW);
glDisable(GL_DEPTH_TEST);
glDisable(GL_LIGHTING);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glEnable(GL_TEXTURE_2D);
glClearColor(0.f, 0.f, 0.f, 0.f);
텍스처 로딩 코드 :
SDL_Surface* s = IMG_Load(toStringz("hello.png"));
if (s == null)
throw new Exception("Image file could not be loaded!");
uint texFormat;
switch (s.format.BytesPerPixel)
{
case 4:
texFormat = (s.format.Rmask == 0x000000ff ? GL_RGBA : GL_BGRA);
break;
case 3:
texFormat = (s.format.Rmask == 0x000000ff ? GL_RGB : GL_BGR);
break;
default:
throw new Exception("Bad pixel format!");
break;
}
if ((s.w & (s.w - 1)) != 0)
throw new Exception("Width must be a power of 2!");
if ((s.h & (s.h - 1)) != 0)
throw new Exception("Height must be a power of 2!");
uint glName;
glGenTextures(1, &glName);
glBindTexture(GL_TEXTURE_2D, glName);
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
glTexImage2D(GL_TEXTURE_2D, 0, s.format.BytesPerPixel, s.w, s.h, 0,
texFormat, GL_UNSIGNED_BYTE, s.pixels);
SDL_FreeSurface(s);
렌더링 코드 :
glClear(GL_COLOR_BUFFER_BIT);
glBegin(GL_QUADS);
glColor4ub(255, 255, 255, 255);
glBindTexture(GL_TEXTURE_2D, glName);
glTexCoord2i(0, 0); glVertex2i(0, 0);
glTexCoord2i(1, 0); glVertex2i(64, 0);
glTexCoord2i(1, 1); glVertex2i(64, 64);
glTexCoord2i(0, 1); glVertex2i(0, 64);
glEnd();
SDL_GL_SwapBuffers();
내 프로그램은 D를 위해 SDL 및 OpenGL 바인딩을 제공하는 Derelict2 라이브러리를 사용합니다.
정확하게 여기에 무슨 문제가 있습니까?
편집 :
http://www.opengl.org/wiki/Common_Mistakes#Creating_a_Texture
내가 전에 glTexImage2D
를 호출하거나 다른 나의 질감이 기술적으로 불완전에 몇 가지 매개 변수를 설정하는 데 필요한 : 미래 참고로, 여기 내 문제의 해결책입니다.
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexImage의 세 번째 매개 변수 인 "format"은 픽셀 당 바이트가 아닙니다. 역사적으로 값 1, 2, 3, 4는 OpenGL-1.0에 의해 수용되었습니다. OpenGL-1 이후.1 이후 형식 매개 변수는 숫자 형식이 실제 형식과 관련이없는 GL_RGBA, GL_RGB 등과 같이 잘 정의 된 토큰 만 받아들입니다. – datenwolf
"OpenGL 초기화"개념을 잊어 버리십시오. 그렇습니다. 텍스처와 물건을로드합니다.하지만 실제 응용 프로그램에서는 이것이 한 번은 아니지만 필요할 때마다 발생합니다. 투영, 투명 색상, 뷰포트 등 모든 렌더링 상태는 렌더링 절차에서 필요하기 바로 전에 설정해야합니다. "OpenGL 초기화 코드"섹션에있는 모든 내용은 "렌더링 코드"섹션의 시작 부분에 속합니다. – datenwolf
@datenwolf : 점 찍었습니다. 귀하의 첫 번째 의견에 관해서는, 내가 사용하고있는 문서는 구형이어야합니다. 그래서 대신 OpenGL enum 값 중 하나를 사용하도록 호출을 업데이트 할 것입니다. 두 번째 주석에 관해서는, 내 특정 응용 프로그램이 장면의 한 관점 만 사용하기 때문에 (즉, 정적 2D보기이므로) 프로젝션, 뷰포트 등과 같은 것들을 초기화 코드에 넣는 것이 내 응용 프로그램에서 적절하다고 생각합니다. 하드웨어 가속 2D 드로잉을 할 수 있습니다.) 나는 당신의 요점을 확실히 본다. – jgottula