2011-08-16 8 views
4

본인은이 source code을 기반으로하며 내 요구 사항에 따라 코드를 변경하려고합니다. 이미지에 메시를 만들기 위해 다음 코드를 포함 시켰습니다.OpenGL iphone SDK에서 메쉬 생성

- 다음 (무효) populateMesh {

verticalDivisions = kVerticalDivisions; 
horizontalDivisions = kHorisontalDivisions; 
unsigned int verticesArrsize = (kVerticalDivisions * ((2 + kHorisontalDivisions * 2) * 3)); 
unsigned int textureCoordsArraySize = kVerticalDivisions * ((2 + kHorisontalDivisions * 2) * 2); 
verticesArr = (GLfloat *)malloc(verticesArrsize * sizeof(GLfloat)); 
textureCoordsArr = (GLfloat*)malloc(textureCoordsArraySize * sizeof(GLfloat)); 
if (verticesArr == NULL) { 
    NSLog(@"verticesArr = NULL!"); 
} 
float height = kWindowHeight/verticalDivisions; 
float width = kWindowWidth/horizontalDivisions; 
int i,j, count; 
count = 0; 
for (j=0; j<verticalDivisions; j++) { 
    for (i=0; i<=horizontalDivisions; i++, count+=6) { //2 vertices each time... 
     float currX = i * width; 
     float currY = j * height; 
     verticesArr[count] = currX; 
     verticesArr[count+1] = currY + height; 
     verticesArr[count+2] = 0.0f;    
     verticesArr[count+3] = currX; 
     verticesArr[count+4] = currY; 
     verticesArr[count+5] = 0.0f; 
    } 
} 
float xIncrease = 1.0f/horizontalDivisions; 
float yIncrease = 1.0f/verticalDivisions; 
int x,y; 
//int elements; 
count = 0; 
for (y=0; y<verticalDivisions; y++) { 
    for (x=0; x<horizontalDivisions+1; x++, count+=4) { 
     float currX = x *xIncrease; 
     float currY = y * yIncrease; 
     textureCoordsArr[count] = (float)currX; 
     textureCoordsArr[count+1] = (float)currY + yIncrease; 
     textureCoordsArr[count+2] = (float)currX; 
     textureCoordsArr[count+3] = (float)currY; 
    } 
} 
// int cnt; 
// int cnt = 0; 
    NSLog(@"expected %i vertices, and %i vertices were done",(verticalDivisions * ((2 + horizontalDivisions*2) * 2)) , count); 
} 

은 drawView 코드입니다. 내가 전화 한 설정보기에서

- (void)drawView:(GLView*)view; 
{ 
static GLfloat rot = 0.0; 
glBindTexture(GL_TEXTURE_2D, texture[0]); 
glClearColor(0.0f, 0.0f, 0.0f, 1.0f); 
glClear(GL_COLOR_BUFFER_BIT); 

glEnableClientState(GL_VERTEX_ARRAY); 
glEnable(GL_TEXTURE_2D); 
glEnableClientState(GL_TEXTURE_COORD_ARRAY); 
glTexCoordPointer(2, GL_FLOAT, 0, textureCoordsArr); 
glVertexPointer(3, GL_FLOAT, 0, verticesArr); 
glPushMatrix();{ 
    int i; 
    for (i=0; i<verticalDivisions; i++) { 
     glDrawArrays(GL_TRIANGLE_STRIP, i*(horizontalDivisions*2+2), horizontalDivisions*2+2); 
    } 
}glPopMatrix(); 
glDisableClientState(GL_VERTEX_ARRAY); 
glDisableClientState(GL_TEXTURE_COORD_ARRAY); 
glDisable(GL_TEXTURE_2D); 
} 

[자기 populateMesh]이 함수의 끝에 있습니다. 내 문제는 코드를 변경 한 후 화면에 검은 색보기가 비어 있다는 뜻입니다. 누군가 내가 실수를하고있는 곳을 알아낼 수 있습니까? 저는 OpenGL에서 초보자이며 메쉬를 통해 이미지를 조작하려고합니다. 가능한 빨리 도와주세요. 미리 감사드립니다.

다음은 설정보기 코드입니다.

-(void)setupView:(GLView*)view {  

const GLfloat zNear = 0.01, zFar = 1000.0, fieldOfView = 45.0; 
GLfloat size; 
glEnable(GL_DEPTH_TEST); 
glMatrixMode(GL_PROJECTION); 
size = zNear * tanf(DEGREES_TO_RADIANS(fieldOfView)/2.0); 
CGRect rect = view.bounds; 
glFrustumf(-size, size, -size/(rect.size.width/rect.size.height), size/ (rect.size.width/rect.size.height), zNear, zFar); 
glViewport(0, 0, rect.size.width, rect.size.height); 
glMatrixMode(GL_MODELVIEW); 
glEnable(GL_TEXTURE_2D); 
glEnable(GL_BLEND); 
glBlendFunc(GL_ONE, GL_SRC_COLOR); 
glGenTextures(1, &texture[0]); 
glBindTexture(GL_TEXTURE_2D, texture[0]); 
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); 
NSString *path = [[NSBundle mainBundle] pathForResource:@"texture" ofType:@"png"]; 
NSData *texData = [[NSData alloc] initWithContentsOfFile:path]; 
UIImage *image = [[UIImage alloc] initWithData:texData]; 
if (image == nil) 
NSLog(@"Do real error checking here");  
GLuint width = CGImageGetWidth(image.CGImage); 
GLuint height = CGImageGetHeight(image.CGImage); 
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 
void *imageData = malloc(height * width * 4); 
CGContextRef context = CGBitmapContextCreate(imageData, width, height, 8, 4 * width, colorSpace, kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big); 

CGContextTranslateCTM (context, 0, height); 

CGContextScaleCTM (context, 1.0, -1.0); 

CGColorSpaceRelease(colorSpace); 

CGContextClearRect(context, CGRectMake(0, 0, width, height)); 

CGContextDrawImage(context, CGRectMake(0, 0, width, height),image.CGImage); 

glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, imageData); 

CGContextRelease(context); 

free(imageData); 
[image release]; 
[texData release]; 
[self populateMesh]; 
} 

편집이 제품은 아웃 넣어 내가 얻고 것입니다. 예상대로 정규 격자입니다 ... enter image description here

+0

모델 및 투영 뷰 매트릭스를 올바르게 설정 했습니까? 행렬 초기 설정 코드를 제공 할 수 있습니까? – Prcela

+0

이미지의 픽셀 크기가 2의 거듭 제곱으로 표시 될 수 있는지 확인하십시오. 예 : 512x512 – Prcela

+0

설정보기 코드가 포함되어 있습니다. populateMesh 함수를 구현하기 전에 이미지를 표시 할 수있었습니다 ... – DivineDesert

답변

2

그리드는 정점 배열 방법에 따라 규칙적이지 않습니다. 또한 GL_TRIANGLE_STRIP이 필요한 옵션인지 확인하십시오. 어쩌면, GL_TRIANGLES가 필요한 것입니다.

인덱스 배열을 사용하면 더 간단한 해결책을 제안합니다.

0 1 2 
3 4 5 
6 7 8 

업데이트 :

- (void) setup 
{ 
    vertices = (GLfloat*)malloc(rows*colums*3*sizeof(GLfloat)); 
    texCoords = (GLfloat*)malloc(rows*columns*2*sizeof(GLfloat)); 
    indices = (GLubyte*)malloc((rows-1)*(columns-1)*6*sizeof(GLubyte)); 

    float xDelta = horizontalDivisions/columns; 
    float yDelta = verticalDivisions/rows; 

    for (int i=0;i<columns;i++) { 
    for(int j=0;j<rows; j++) { 
     int index = j*columns+i; 
     vertices[3*index+0] = i*xDelta; //x 
     vertices[3*index+1] = j*yDelta; //y 
     vertices[3*index+2] = -10; //z 

     texCoords[2*index+0] = i/(float)(columns-1); //x texture coordinate 
     texCoords[2*index+1] = j/(float)(rows-1); //y tex coordinate 
    } 
    } 

    for (int i=0;i<columns-1;i++) { 
    for(int j=0;j<rows-1; j++) { 

    indices[6*(j*columns+i)+0] = j*columns+i; 
    indices[6*(j*columns+i)+1] = j*columns+i+1; 
    indices[6*(j*columns+i)+2] = (j+1)*columns+i; 

    indices[6*(j*columns+i)+3] = j*columns+i+1; 
    indices[6*(j*columns+i)+4] = (j+1)*columns+i+1; 
    indices[6*(j*columns+i)+5] = (j+1)*columns+i; 
    } 
} 
} 

- (void) dealloc { 
    free(vertices); free(texCoords); free(indices); 
} 

가 실질적으로이 순서는 tringles은 다음으로 렌더링되는 것을 의미와 indices :

초기화 코드에서 예를 들어 정상 순서대로 그리드 정점과 텍스처 배열을
(013)(143)(124)(254)(346)(476)... and so on. 

render 메서드에서 다음 줄을 사용하십시오.

glVertexPointer(3, GL_FLOAT, 0, vertices); 
glTexCoordPointer(2, GL_FLOAT, 0, texCoords); 
glDrawElements(GL_TRIANGLES, 6*(columns-1)*(rows-1), GL_UNSIGNED_BYTE, indices); 

희망이 도움이 될 것입니다.

+0

그래서 요소를 그릴 루프가 필요하지 않습니까 ??? – DivineDesert

+0

안녕하세요 .. 그게 나를 위해 작동하지 않습니다 ... u 정교한 수 있습니까 ??? – DivineDesert

+0

작은 업데이트가 추가되었습니다. 요소를 그리기위한 루프가 필요 없습니다. 더 간단한 솔루션. 나는 코드를 테스트하지 않았고, 머리에서 작성하여 버그를 포함 할 수 있지만 개념은 분명합니다. – Prcela

3

zNear 값으로 격자를 잘라냅니다. z 값을 -2로 변경하십시오. 기본적

verticesArr[count+2] = -2.0f; 
verticesArr[count+5] = -2.0f; 

가 카메라를 원점에 위치하고, 마이너스 Z 축 아래 지점과의 업 벡터를 갖고 (0, 1, 0).

메쉬가 시야 절두체 (피라미드)를 벗어 났음을 알 수 있습니다. OpenGL은 빨간 책에서 체크 아웃 :

http://glprogramming.com/red/chapter03.html

+0

답장을 보내 주셔서 감사합니다 ... ur 변경 사항을 편집하고 glFrustumf() 문을 주석 처리 한 후 위의 뷰를 얻고 있습니다. 이전에 가지고 있었던 것보다 많은 차이가 없습니다. 아직 다른 뭔가 잘못되고있어 ... 알아낼 수있어 ??? – DivineDesert

1

This 차원에서 그리드 그리기에 좋은 튜토리얼입니다. 그것은 당신을 돕는 데 필요한 코드가 있어야합니다. 3D 또는 2D로 작업하는지 확신 할 수 없지만 2D 일지라도 사용자의 요구에 쉽게 적응할 수 있어야합니다. 희망이 도움이됩니다!