2014-02-12 43 views
1

我正在使用OpenGL ES(2.0)专门为我的应用程序。我试图让UIMotionEffect与我的一个OpenGL对象一起工作 - 我需要的就是“倾斜”值。使用UIMotionEffect与OpenGL ES

UIInterpolatingMotionEffect只能应用于UIView,和一个黑客将适用UIInterpolatingMotionEffectUIView,并从每帧有抢值,而不是渲染所谓UIView。但似乎太过黑客 - 是唯一的解决方案。

我试图将子类UIMotionEffect,但无法弄清楚如何- (NSDictionary *)keyPathsAndRelativeValuesForViewerOffset:(UIOffset)viewerOffset工作(即什么调用它,以及如何检索我需要的值)。

关于如何在OpenGL上使用UIMotionEffect的任何想法?

回答

5

我最终测试了@rickster建议的方法:将UIInterpolatingMotionEffect连接到我的GLKView/GL View传递键定制,并检索它们。不幸的是,这个想法完全失败了。

首先,传递给UIInterpolatingMotionEffect的键必须是UIView的动画属性,并且不能是自定义变量/属性。考虑到大多数人不希望他们的整个背景以单向方向/强度的视差,这种方法将失败。

其次,你不能只检索值。如果您通过center.x作为关键字,UIInterpolatingMotionEffect将不会更新center.x,因为这些更改被视为“动画”。因此,你有你检索动画center.x,例如[[view.layer presentationLayer] center];

最后说明:只要在主线程中创建一个单独的UIView,把它添加到您的UIViewController,系统从中检索值(也主线程)。我发现这是迄今为止最简单的解决方案。因为我需要在一个单独的线程上检索这些值,所以我通常会将1值放在后面,因为我派发到主线程来检索当前值,同时检索最后一个值集(确保变量是线程安全的/原子的)。

编辑

由于其最佳进入主线程的表示层,但我的方法被称为一个线程,是不是主要的,我派遣主线程检索值,并将其放置在原子属性。然后我会返回线程外的atomic属性。这可以确保我的辅助线程不会被主线程阻塞,并且可以检索我需要的值。

这里是我以前从一个线程是不是主线程中检索值的代码:

@property (atomic) GLKVector2 currentOffset; 
@property (atomic, readonly) GLKVector2 offset; 

- (GLKVector2)offset 
{ 
    dispatch_async(dispatch_get_main_queue(), ^{ 
     CGRect frame = [[self.view.layer presentationLayer] frame]; 
     self.currentOffset = (GLKVector2){-frame.origin.x, -frame.origin.y}; 
    }); 

    return self.currentOffset; 
} 
+0

你能提供在第4段,在这里回答你的问题更详细? –

+0

@JohnStephen做:) –

+0

谢谢,这是非常有益的! –

1

UIInterpolatingMotionEffect通过使用键值编码为UIView上的任何数值属性设置值。这可以是您定义的任何属性,而不仅仅是内置到UIView类中的那些属性。

您需要某种UIView才能在屏幕上显示您的内容。如果你在iOS上使用OpenGL ES,你最好使用GLKView,这是一个UIView子类,它管理着自己的GL帧缓冲区,并为你提供了一个编写GL绘图代码以渲染到这些帧缓冲区的地方。 (如果你不使用GLKView,你可能会使用某种自定义的UIView子类,它使用一个CAEAGLLayer呈现其内容。)

无论哪种方式,如果你已经有了GL-呈现的内容在屏幕上已经,你已经有一个UIView。如果该视图不是您自己的自定义子类(无论是直接UIView子类还是GLKView子类),则可以将其设为一个,并在其上定义自己的自定义属性。然后设置您的UIInterpolatingMotionEffect以使用这些属性。在您的视图子类中,或任何负责GL渲染的对象中,读取这些属性的值并使用它们设置场景。 (例如,您可以使用它们来设置ModelView矩阵,并将其传递给着色器制服。)