2015-01-17 16 views
5

Ich folge this tutorial über OpenGL/GLKit für iOS, aber versuche es in Swift zu implementieren. Es geht gut, bis ich zu diesem Teil erhalten:Wie konvertiere ich diese OpenGL-Zeiger-Mathematik in Swift?

- (void)render { 

// 1 
self.effect.texture2d0.name = self.textureInfo.name; 
self.effect.texture2d0.enabled = YES; 

// 2  
[self.effect prepareToDraw]; 

// 3 
glEnableVertexAttribArray(GLKVertexAttribPosition); 
glEnableVertexAttribArray(GLKVertexAttribTexCoord0); 

//---------------- This is where things break down... 
long offset = (long)&_quad;   
glVertexAttribPointer(GLKVertexAttribPosition, 2, GL_FLOAT, GL_FALSE, sizeof(TexturedVertex), (void *) (offset + offsetof(TexturedVertex, geometryVertex))); 
glVertexAttribPointer(GLKVertexAttribTexCoord0, 2, GL_FLOAT, GL_FALSE, sizeof(TexturedVertex), (void *) (offset + offsetof(TexturedVertex, textureVertex))); 

// 5  
glDrawArrays(GL_TRIANGLE_STRIP, 0, 4); 

} 

@end 

Ich habe eine Eigenschaft self.quad, die eine Swift-Struktur wie folgt ist:

struct TexturedVertex { 
let geometryVertex: CGPoint 
let textureVertex: CGPoint 
} 

struct TexturedQuad { 

let bottomLeft: TexturedVertex 
let bottomRight: TexturedVertex 
let topLeft: TexturedVertex 
let topRight: TexturedVertex 
} 

Es ist eine ziemlich einfache Struktur, aber Ich weiß nicht, wie um es zum letzten Argument von glVertexAttribPointer zu übergeben. Jede Hilfe wäre hervorragend!

Antwort

10

In Swift können Sie die generische Struktur UnsafePointer verwenden, um Zeigerarithmetik und Casting durchzuführen. Swift hat keine offsetof, aber Sie können das sauber umgehen, indem Sie UnsafePointer s der geometryVertex und textureVertex Elemente direkt nehmen.

Der folgende Code wird in einem iOS-Spielplatz kompiliert. Ich habe es nicht darüber hinaus getestet, aber ich denke, es arbeiten werde:

import OpenGLES 
import GLKit 

struct TexturedVertex { 
    var geometryVertex = GLKVector2() 
    var textureVertex = GLKVector2() 
} 

struct TexturedQuad { 
    var bl = TexturedVertex() 
    var br = TexturedVertex() 
    var tl = TexturedVertex() 
    var tr = TexturedVertex() 
    init() { } 
} 

var _quad = TexturedQuad() 
withUnsafePointer(&_quad.bl.geometryVertex) { (pointer) -> Void in 
    glVertexAttribPointer(GLuint(GLKVertexAttrib.Position.rawValue), 
     2, GLenum(GL_FLOAT), GLboolean(GL_FALSE), 
     GLsizei(sizeof(TexturedVertex)), pointer) 
} 
withUnsafePointer(&_quad.bl.textureVertex) { (pointer) -> Void in 
    glVertexAttribPointer(GLuint(GLKVertexAttrib.TexCoord0.rawValue), 
     2, GLenum(GL_FLOAT), GLboolean(GL_FALSE), 
     GLsizei(sizeof(TexturedVertex)), pointer) 
} 

By the way, mit CGPoint so, wie Sie in Ihrer Frage sind gefährlich, weil CGFloat Änderungen auf Ihrer Zielgröße abhängig (32- Bit oder 64-Bit), aber GL_FLOAT bedeutet immer 32-Bit. Das Tutorial, dem Sie folgen, wurde geschrieben, bevor 64-Bit-iOS herauskam.

+0

Ausgezeichnet! Ich füge auch noch das nächste Problem in das Tutorial ein, da die meisten von GLKit in Swift kaputt sind, weil Swift 'union' fehlt. Dieses Bit Code umgeht das Problem obwohl https://github.com/programmingthomas/OpenGL.swift – jbrennan

+0

Auch, ja, 'CGPoint' funktioniert nicht, weil die Schwimmer zu groß sind. Sie müssen 32 Bit 'GL_FLOAT' verwenden. – jbrennan