(iOS) Приложение OpenGL ES (2.0), как переместить объект в Z? - PullRequest
1 голос
/ 25 ноября 2010

Я играю с исходным кодом OpenGL ES (2.0) приложения (iOS) в XCode и пытался заставить цветной квадрат двигаться в координате Z, поэтому я попытался изменить код шейдера с

gl_Position.y + = sin (перевод) / 2.0;

до

gl_Position.z + = sin (перевод) / 2.0;без успеха.

Квадрат не двигается вообще.Он хорошо двигается в X и Y подумал ... Есть ли какая-то опция, которую мне нужно активировать при инициализации OpenGL?Спасибо!

ОБНОВЛЕНИЕ: Я загрузил пример.Это примерно шаблон OpenGL ES, который генерирует XCode, я просто добавил вызовы для создания буфера глубины и gl_Position.x в gl_Position.z + = sin (translate) / 2.0f в Shader.vsh.

Я бы хотел видеть движение квадрата в синусоидальной форме по координате Z, но это не так.Либо он остается неподвижным, либо, если я умножу грех (), он будет появляться и исчезать в цикле.

Если кто-нибудь может мне помочь, я буду очень благодарен, так как искренне я не знаю, что ещечтобы сделать, и поверьте мне, я много пробовал ...

Источник в zip по адресу: http://cl.ly/24240x2D1t2A3I0c1l1P

Спасибо!

Ответы [ 2 ]

2 голосов
/ 25 ноября 2010

В рассматриваемом примере нет буфера глубины и матрицы перспективы, предназначенной для 2D GL.Взгляните на пример aurioTouch.в классе EAGLView вы заметите опцию для реализации буфера глубины.Обе комбинации (поскольку aurioTouch не реализует шейдеры) должны дать лучшее понимание

Я думаю, что порядок операций, которые вы используете в своем методе, вызывает проблему.Вот код, который я использую в своем приложении «Live Effects Cam», которое помещает живую камеру в виде текстуры GL на фигуры:

#define DEGREES_TO_RADIANS(__ANGLE__) ((__ANGLE__) / 180.0 * M_PI)



@interface GLView : UIView
    {
@private
    /* The pixel dimensions of the backbuffer */
    GLint backingWidth;
    GLint backingHeight;

    EAGLContext *context;

    /* OpenGL names for the renderbuffer and framebuffers used to render to this view */
    GLuint viewRenderbuffer;
    GLuint viewFramebuffer;
    GLuint depthRenderbuffer;

    /* OpenGL name for the sprite texture */
    GLuint spriteTexture;
    }

@property (readonly) GLint backingWidth;
@property (readonly) GLint backingHeight;
@property (readonly) EAGLContext *context;


- (void) drawView;
- (BOOL) createFramebuffer;
- (void) destroyFramebuffer;
+ (UIImage *) snapshot:(GLView *)eaglview;

@end




@implementation GLView


@synthesize backingWidth;
@synthesize backingHeight;
@synthesize context;


+ (Class) layerClass
    {
    return [CAEAGLLayer class];
    }



- (id)init
    {
    self = [[super init] initWithFrame:CGRectMake(0.0, 0.0, 480.0, 640.0)];     // size of the camera image being captures

    if ( self==nil )
        return self;


    // Set Content Scaling
    //
    if ( HIRESDEVICE )
        {
        self.contentScaleFactor = (CGFloat)2.0;
        }

    // Get our backing layer
    //
    CAEAGLLayer *eaglLayer = (CAEAGLLayer*) self.layer;

    // Configure it so that it is opaque, does not retain the contents of the backbuffer when displayed, and uses RGBA8888 color.
    //
    eaglLayer.opaque = YES;

    eaglLayer.drawableProperties = [NSDictionary dictionaryWithObjectsAndKeys:
                                        [NSNumber numberWithBool:FALSE], kEAGLDrawablePropertyRetainedBacking,
                                        kEAGLColorFormatRGBA8, kEAGLDrawablePropertyColorFormat,
                                        nil];

    // Create our EAGLContext, and if successful make it current and create our framebuffer.
    //
    context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES1];

    if(!context || ![EAGLContext setCurrentContext:context] || ![self createFramebuffer])
        {
        [self release];
        return nil;
        }

    // Final View Settings
    //
    [self setOpaque:YES];
    self.multipleTouchEnabled = YES;
    self.backgroundColor = [UIColor clearColor];

    [EAGLContext setCurrentContext:context];

    glBindFramebufferOES(GL_FRAMEBUFFER_OES, viewFramebuffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, viewRenderbuffer);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();

    GLfloat zNear = 1.0;
    GLfloat zFar = 1000.0;
    GLfloat fieldOfView = 90;       // Lens Angle of View
    GLfloat size = zNear * tanf(DEGREES_TO_RADIANS(fieldOfView) / 2.0);
    CGRect rect = CGRectMake( (CGFloat)0.0, (CGFloat)0.0, backingWidth, backingHeight);

    glFrustumf(-size, size, -size / (rect.size.width / rect.size.height), size / (rect.size.width / rect.size.height), zNear, zFar);

    glViewport(0, 0, backingWidth, backingHeight);

    glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    glEnable(GL_DEPTH_TEST);
    glDepthFunc(GL_LESS);
    glEnable(GL_MULTISAMPLE);
    glEnable(GL_LINE_SMOOTH);
    glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);  
    glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);  
    glHint(GL_POINT_SMOOTH_HINT, GL_NICEST);  
    glDisable(GL_ALPHA_TEST);

    // Turn Translucent Textures: OFF
    //
    glDisable(GL_BLEND);

//  // Turn Translucent Textures: ON
//  //
//  glEnable(GL_BLEND);
//  glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);

    return self;
    }



- (void) drawView
    {
    [context presentRenderbuffer:GL_RENDERBUFFER_OES];
    }




- (BOOL)createFramebuffer
    {
    // Generate IDs for a framebuffer object and a color renderbuffer
    //
    glGenFramebuffersOES(1, &viewFramebuffer);
    glGenRenderbuffersOES(1, &viewRenderbuffer);

    glBindFramebufferOES(GL_FRAMEBUFFER_OES, viewFramebuffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, viewRenderbuffer);

    // This call associates the storage for the current render buffer with the EAGLDrawable (our CAEAGLLayer)
    // allowing us to draw into a buffer that will later be rendered to screen whereever the layer is (which corresponds with our view).
    //
    [context renderbufferStorage:GL_RENDERBUFFER_OES fromDrawable:(CAEAGLLayer*)self.layer];

    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, viewRenderbuffer);

    glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_WIDTH_OES, &backingWidth);
    glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_HEIGHT_OES, &backingHeight);

    // If this app uses a depth buffer, we'll create and attach one via another renderbuffer.
    //
    if ( YES )
        {
        glGenRenderbuffersOES(1, &depthRenderbuffer);
        glBindRenderbufferOES(GL_RENDERBUFFER_OES, depthRenderbuffer);
        glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES, backingWidth, backingHeight);
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, depthRenderbuffer);
        }   

    if(glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES) != GL_FRAMEBUFFER_COMPLETE_OES)
        {
        NSLog(@"failed to make complete framebuffer object %x", glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES));
        return NO;
        }

    return YES;
    }


- (void) destroyFramebuffer
    {
    glDeleteFramebuffersOES(1, &viewFramebuffer);
    viewFramebuffer = 0;

    glDeleteRenderbuffersOES(1, &viewRenderbuffer);
    viewRenderbuffer = 0;

    if(depthRenderbuffer)
        {
        glDeleteRenderbuffersOES(1, &depthRenderbuffer);
        depthRenderbuffer = 0;
        }
    }




+ (UIImage *) snapshot:(GLView *)eaglview
    {
    NSInteger x = 0;
    NSInteger y = 0;
    NSInteger width = [eaglview backingWidth];
    NSInteger height = [eaglview backingHeight];
    NSInteger dataLength = width * height * 4;

// Need to do this to get it to flush before taking the snapshit
//
    NSUInteger i;
    for ( i=0; i<100; i++ )
        {
        glFlush();
        CFRunLoopRunInMode(kCFRunLoopDefaultMode, (float)1.0/(float)60.0, FALSE);
        }

    GLubyte *data = (GLubyte*)malloc(dataLength * sizeof(GLubyte));

    // Read pixel data from the framebuffer
    //
    glPixelStorei(GL_PACK_ALIGNMENT, 4);
    glReadPixels(x, y, width, height, GL_RGBA, GL_UNSIGNED_BYTE, data);

    // Create a CGImage with the pixel data
    // If your OpenGL ES content is opaque, use kCGImageAlphaNoneSkipLast to ignore the alpha channel
    // otherwise, use kCGImageAlphaPremultipliedLast
    //
    CGDataProviderRef ref = CGDataProviderCreateWithData(NULL, data, dataLength, NULL);
    CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceRGB();
    CGImageRef iref = CGImageCreate(width, height, 8, 32, width * 4, colorspace, kCGBitmapByteOrder32Big | kCGImageAlphaPremultipliedLast, ref, NULL, true, kCGRenderingIntentDefault);

    // OpenGL ES measures data in PIXELS
    // Create a graphics context with the target size measured in POINTS
    //
    NSInteger widthInPoints;
    NSInteger heightInPoints;

    if (NULL != UIGraphicsBeginImageContextWithOptions)
        {
        // On iOS 4 and later, use UIGraphicsBeginImageContextWithOptions to take the scale into consideration
        // Set the scale parameter to your OpenGL ES view's contentScaleFactor
        // so that you get a high-resolution snapshot when its value is greater than 1.0
        //
        CGFloat scale = eaglview.contentScaleFactor;
        widthInPoints = width / scale;
        heightInPoints = height / scale;
        UIGraphicsBeginImageContextWithOptions(CGSizeMake(widthInPoints, heightInPoints), NO, scale);
        }
    else
        {
        // On iOS prior to 4, fall back to use UIGraphicsBeginImageContext
        //
        widthInPoints = width;
        heightInPoints = height;
        UIGraphicsBeginImageContext(CGSizeMake(widthInPoints, heightInPoints));
        }

    CGContextRef cgcontext = UIGraphicsGetCurrentContext();

    // UIKit coordinate system is upside down to GL/Quartz coordinate system
    // Flip the CGImage by rendering it to the flipped bitmap context
    // The size of the destination area is measured in POINTS
    //
    CGContextSetBlendMode(cgcontext, kCGBlendModeCopy);
    CGContextDrawImage(cgcontext, CGRectMake(0.0, 0.0, widthInPoints, heightInPoints), iref);

    // Retrieve the UIImage from the current context
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();   // autoreleased image

    UIGraphicsEndImageContext();

    // Clean up
    free(data);
    CFRelease(ref);
    CFRelease(colorspace);
    CGImageRelease(iref);

    return image;
    }


@end
0 голосов
/ 26 ноября 2010
    // Create default framebuffer object.
    glGenFramebuffers(1, &defaultFramebuffer);
    glBindFramebuffer(GL_FRAMEBUFFER, defaultFramebuffer);

    // Create color render buffer and allocate backing store.
    glGenRenderbuffers(1, &depthRenderbuffer); <----
    glGenRenderbuffers(1, &colorRenderbuffer);

    glBindRenderbuffer(GL_RENDERBUFFER, depthRenderbuffer); <----
    glBindRenderbuffer(GL_RENDERBUFFER, colorRenderbuffer);

    [context renderbufferStorage:GL_RENDERBUFFER fromDrawable:(CAEAGLLayer *)self.layer];

    glGetRenderbufferParameteriv(GL_RENDERBUFFER, GL_RENDERBUFFER_WIDTH, &framebufferWidth);
    glGetRenderbufferParameteriv(GL_RENDERBUFFER, GL_RENDERBUFFER_HEIGHT, &framebufferHeight);

    glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, framebufferWidth, framebufferHeight); <----

    glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorRenderbuffer);
    glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depthRenderbuffer); <----

Я добавил это в свой код (... <----) и теперь у меня розоватый экран (смеется). Есть идеи? Это действительно расстраивает. Разве я не должен делать что-то в setFrame .. presentFrame ..? </p>

...