add support for CADisplayLink

This commit is contained in:
Rhody Lugo 2015-02-10 15:24:22 -04:30
parent 66d32b75b3
commit d67e866788
2 changed files with 40 additions and 0 deletions

View file

@ -34,6 +34,8 @@
#import <MediaPlayer/MediaPlayer.h> #import <MediaPlayer/MediaPlayer.h>
#import <AVFoundation/AVFoundation.h> #import <AVFoundation/AVFoundation.h>
#define USE_CADISPLAYLINK 1 //iOS version 3.1+ is required
@protocol GLViewDelegate; @protocol GLViewDelegate;
@interface GLView : UIView<UIKeyInput> @interface GLView : UIView<UIKeyInput>
@ -51,8 +53,14 @@
// OpenGL name for the depth buffer that is attached to viewFramebuffer, if it exists (0 if it does not exist) // OpenGL name for the depth buffer that is attached to viewFramebuffer, if it exists (0 if it does not exist)
GLuint depthRenderbuffer; GLuint depthRenderbuffer;
#if USE_CADISPLAYLINK
// CADisplayLink available on 3.1+ synchronizes the animation timer & drawing with the refresh rate of the display, only supports animation intervals of 1/60 1/30 & 1/15
CADisplayLink *displayLink;
#else
// An animation timer that, when animation is started, will periodically call -drawView at the given rate. // An animation timer that, when animation is started, will periodically call -drawView at the given rate.
NSTimer *animationTimer; NSTimer *animationTimer;
#endif
NSTimeInterval animationInterval; NSTimeInterval animationInterval;
// Delegate to do our drawing, called by -drawView, which can be called manually or via the animation timer. // Delegate to do our drawing, called by -drawView, which can be called manually or via the animation timer.

View file

@ -413,7 +413,19 @@ static void clear_touches() {
return; return;
active = TRUE; active = TRUE;
printf("start animation!\n"); printf("start animation!\n");
#if USE_CADISPLAYLINK
// Approximate frame rate
// assumes device refreshes at 60 fps
int frameInterval = (int) floor(animationInterval * 60.0f);
displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(drawView)];
[displayLink setFrameInterval:frameInterval];
// Setup DisplayLink in main thread
[displayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSRunLoopCommonModes];
#else
animationTimer = [NSTimer scheduledTimerWithTimeInterval:animationInterval target:self selector:@selector(drawView) userInfo:nil repeats:YES]; animationTimer = [NSTimer scheduledTimerWithTimeInterval:animationInterval target:self selector:@selector(drawView) userInfo:nil repeats:YES];
#endif
if (video_playing) if (video_playing)
{ {
@ -427,8 +439,13 @@ static void clear_touches() {
return; return;
active = FALSE; active = FALSE;
printf("******** stop animation!\n"); printf("******** stop animation!\n");
#if USE_CADISPLAYLINK
[displayLink invalidate];
displayLink = nil;
#else
[animationTimer invalidate]; [animationTimer invalidate];
animationTimer = nil; animationTimer = nil;
#endif
clear_touches(); clear_touches();
if (video_playing) if (video_playing)
@ -441,7 +458,11 @@ static void clear_touches() {
{ {
animationInterval = interval; animationInterval = interval;
#if USE_CADISPLAYLINK
if(displayLink)
#else
if(animationTimer) if(animationTimer)
#endif
{ {
[self stopAnimation]; [self stopAnimation];
[self startAnimation]; [self startAnimation];
@ -451,6 +472,17 @@ static void clear_touches() {
// Updates the OpenGL view when the timer fires // Updates the OpenGL view when the timer fires
- (void)drawView - (void)drawView
{ {
#if USE_CADISPLAYLINK
// Pause the CADisplayLink to avoid recursion
[displayLink setPaused: YES];
// Process all input events
while(CFRunLoopRunInMode(kCFRunLoopDefaultMode, 0, TRUE) == kCFRunLoopRunHandledSource);
// We are good to go, resume the CADisplayLink
[displayLink setPaused: NO];
#endif
if (!active) { if (!active) {
printf("draw view not active!\n"); printf("draw view not active!\n");
return; return;