4

这里是 OpenGL ES 的新手。我正在使用以下代码来检测我在 GLKView (OpenGL ES 2.0) 中点击的位置。我想知道我是否触摸了我的 OpenGL 绘制对象。都是二维的。如何将我得到的坐标转换为基于 -1.0 到 1.0 的 OpenGL ES 2.0 坐标?是否已经有内置功能可以做到这一点?

谢谢。

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
    CGRect bounds = [self.view bounds];

    UITouch* touch = [[event touchesForView:self.view] anyObject];

    CGPoint location = [touch locationInView:self.view];

    NSLog(@"x: %f y: %f", location.x, location.y);

}
4

1 回答 1

2

-1 到 1 是剪裁空间。如果您的坐标空间在屏幕上显示时位于裁剪空间中,我会说您忘记使用投影矩阵转换空间。如果您正在使用GLKBaseEffect(我不建议以后使用,因为它往往会到处发生内存泄漏),那么您需要设置<baseEffect>.transform.projectionMatrix一个可以正确转换空间的矩阵。例如,

GLKBaseEffect* effect = [[GLKBaseEffect alloc] init];
GLKMatrix4 projectionMatrix = GLKMatrix4MakeOrtho(0, <width>, 0, <height>, 0.0f, 1.0f);
self.effect.transform.projectionMatrix = projectionMatrix;

width并且height将是设备屏幕/您的GLKView/等的宽度和高度。这会自动应用于您传入的坐标,以便您可以使用从 0 到轴和 0 到轴的正常坐标,<width>原点x位于<height>屏幕y的左下角。

如果您像我一样使用自定义着色器,那么您可以使用以下方法将投影矩阵作为统一传递: glUniformMatrix4fv(shaderLocations.projectionMatrix,1,0,projection.m)

正如他们所说,矩阵在哪里projection,并且shaderLocations.projectionMatrix是制服名称的标识符。然后,您需要将您的位置乘以投影矩阵。

一旦你从裁剪空间转换出来,无论是通过手动传递矩阵还是设置正确的属性 on GLKBaseEffect,OpenGL 空间和 UIKit 空间之间的唯一区别是y轴被翻转。touches我通过这样的方法和手势识别器转换我收到的触摸。

CGPoint openGLTouch = CGPointMake(touch.x, self.view.bounds.size.height - touch.y);

如果您有任何问题,我会尽力澄清,但请记住,我本人对 OpenGL 还比较陌生。:)

于 2013-02-05T08:30:57.013 回答