gpmark

view src/ios/glview.mm @ 0:5019d031b485

initial commit
author John Tsiombikas <nuclear@member.fsf.org>
date Wed, 05 Jun 2013 22:33:37 +0300
parents
children
line source
1 #import "glview.h"
2 #include "game.h"
3 #include "screen.h"
4 #include "logger.h"
6 static GLView *view;
8 void request_redisplay()
9 {
10 // TODO
11 }
13 void swap_buffers()
14 {
15 if(view) {
16 [view swap_buffers];
17 }
18 }
21 @implementation GLView
23 @synthesize animating;
24 @dynamic anim_frame_interval;
26 // You must implement this method
27 + (Class)layerClass
28 {
29 return [CAEAGLLayer class];
30 }
33 - (id)initWithFrame: (CGRect) frame
34 {
35 if((self = [super initWithFrame: frame]))
36 {
37 // Get the layer
38 CAEAGLLayer *eaglLayer = (CAEAGLLayer*)self.layer;
40 //self.contentScaleFactor = 2.0;
42 eaglLayer.opaque = TRUE;
43 eaglLayer.drawableProperties = [NSDictionary dictionaryWithObjectsAndKeys: [NSNumber numberWithBool:FALSE],
44 kEAGLDrawablePropertyRetainedBacking, kEAGLColorFormatRGBA8,
45 kEAGLDrawablePropertyColorFormat, nil];
47 // initialize OpenGL ES context
48 context = [[EAGLContext alloc] initWithAPI: kEAGLRenderingAPIOpenGLES2];
49 if(!context || ![EAGLContext setCurrentContext: context]) {
50 [self release];
51 return self;
52 }
54 // create the framebuffer
55 glGenFramebuffers(1, &fbo);
56 glBindFramebuffer(GL_FRAMEBUFFER, fbo);
58 glGenRenderbuffers(1, &rbuf_color);
59 glBindRenderbuffer(GL_RENDERBUFFER, rbuf_color);
60 glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rbuf_color);
62 glGenRenderbuffers(1, &rbuf_depth);
63 glBindRenderbuffer(GL_RENDERBUFFER, rbuf_depth);
64 glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rbuf_depth);
66 animating = FALSE;
67 display_link_supported = FALSE;
68 anim_frame_interval = 1;
69 display_link = nil;
70 anim_timer = nil;
72 // A system version of 3.1 or greater is required to use CADisplayLink. The NSTimer
73 // class is used as fallback when it isn't available.
74 NSString *reqSysVer = @"3.1";
75 NSString *currSysVer = [[UIDevice currentDevice] systemVersion];
76 if([currSysVer compare: reqSysVer options: NSNumericSearch] != NSOrderedAscending) {
77 display_link_supported = TRUE;
78 }
80 self.multipleTouchEnabled = 1;
82 if(!game_init()) {
83 exit(1);
84 }
85 }
87 view = self;
88 return self;
89 }
91 - (void)drawView: (id)sender
92 {
93 game_display();
94 }
96 - (void)swap_buffers
97 {
98 glBindRenderbuffer(GL_RENDERBUFFER, rbuf_color);
99 [context presentRenderbuffer: GL_RENDERBUFFER];
100 }
102 - (BOOL)resize: (CAEAGLLayer*)layer
103 {
104 glBindRenderbuffer(GL_RENDERBUFFER, rbuf_color);
105 [context renderbufferStorage: GL_RENDERBUFFER fromDrawable: layer];
106 glGetRenderbufferParameteriv(GL_RENDERBUFFER, GL_RENDERBUFFER_WIDTH, &xsz);
107 glGetRenderbufferParameteriv(GL_RENDERBUFFER, GL_RENDERBUFFER_HEIGHT, &ysz);
109 glBindRenderbuffer(GL_RENDERBUFFER, rbuf_depth);
110 glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, xsz, ysz);
112 if(glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) {
113 NSLog(@"resize failed, framebuffer incomplete\n");
114 return FALSE;
115 }
116 assert(glGetError() == GL_NO_ERROR);
118 //current_screen()->reshape(xsz, ysz);
119 return TRUE;
120 }
122 - (void)layoutSubviews
123 {
124 [self resize: (CAEAGLLayer*)self.layer];
125 [self drawView:nil];
126 }
128 - (NSInteger)anim_frame_interval
129 {
130 return anim_frame_interval;
131 }
133 - (void)setAnimationFrameInterval: (NSInteger)frameInterval
134 {
135 // Frame interval defines how many display frames must pass between each time the
136 // display link fires. The display link will only fire 30 times a second when the
137 // frame internal is two on a display that refreshes 60 times a second. The default
138 // frame interval setting of one will fire 60 times a second when the display refreshes
139 // at 60 times a second. A frame interval setting of less than one results in undefined
140 // behavior.
141 if(frameInterval >= 1) {
142 anim_frame_interval = frameInterval;
144 if(animating) {
145 [self stopAnimation];
146 [self startAnimation];
147 }
148 }
149 }
151 - (void)startAnimation
152 {
153 if(!animating) {
154 if(display_link_supported) {
155 // CADisplayLink is API new to iPhone SDK 3.1. Compiling against earlier versions will result in a warning, but can be dismissed
156 // if the system version runtime check for CADisplayLink exists in -initWithCoder:. The runtime check ensures this code will
157 // not be called in system versions earlier than 3.1.
159 display_link = [NSClassFromString(@"CADisplayLink") displayLinkWithTarget:self selector:@selector(drawView:)];
160 [display_link setFrameInterval: anim_frame_interval];
161 [display_link addToRunLoop: [NSRunLoop currentRunLoop] forMode: NSDefaultRunLoopMode];
162 } else {
163 anim_timer = [NSTimer scheduledTimerWithTimeInterval: (NSTimeInterval)((1.0 / 60.0) * anim_frame_interval)
164 target: self selector: @selector(drawView:) userInfo: nil repeats: TRUE];
165 }
167 animating = TRUE;
168 }
169 }
171 - (void)stopAnimation
172 {
173 if(animating) {
174 if(display_link_supported) {
175 [display_link invalidate];
176 display_link = nil;
177 } else {
178 [anim_timer invalidate];
179 anim_timer = nil;
180 }
182 animating = FALSE;
183 }
184 }
186 - (void)dealloc
187 {
188 game_cleanup();
190 if(fbo) {
191 glDeleteFramebuffers(1, &fbo);
192 fbo = 0;
193 }
194 if(rbuf_color) {
195 glDeleteRenderbuffers(1, &rbuf_color);
196 rbuf_color = 0;
197 }
198 if(rbuf_depth) {
199 glDeleteRenderbuffers(1, &rbuf_depth);
200 rbuf_depth = 0;
201 }
203 if([EAGLContext currentContext] == context) {
204 [EAGLContext setCurrentContext: nil];
205 }
206 [context release];
207 context = nil;
209 [super dealloc];
210 }
212 @end