Skip to content

Instantly share code, notes, and snippets.

@SuperDoxin
Last active August 29, 2015 14:05
Show Gist options
  • Select an option

  • Save SuperDoxin/95eb7b5f301a01af56a4 to your computer and use it in GitHub Desktop.

Select an option

Save SuperDoxin/95eb7b5f301a01af56a4 to your computer and use it in GitHub Desktop.
attempt at python/sdl/opengl3
#version 330 core
in vec2 pos;
out vec4 color_out;
void main()
{
color_out=vec4(1.0,0.0,0.0,1.0);
}
from __future__ import division
import sdl2
import sdl2.ext
import atexit
import OpenGL.GL as gl
import numpy as np
import Image
import OpenGL.GL.shaders as shaders
def getshaderlog(shader):
#ln=gl.glGetShaderiv(shader,gl.GL_INFO_LOG_LENGTH)
return gl.glGetShaderInfoLog(shader)
class ShaderProgram(object):
activeshader=None
def __init__(self,name):
with open(name+".vertex.glsl","r") as fid:
vertex=fid.read()
with open(name+".fragment.glsl","r") as fid:
fragment=fid.read()
#vertexshader=gl.glCreateShader(gl.GL_VERTEX_SHADER)
#gl.glShaderSource(vertexshader,1,vertex)
#gl.glCompileShader(vertexshader)
try:
vertexshader=shaders.compileShader(vertex, gl.GL_VERTEX_SHADER)
except RuntimeError as ex:
print ex[0]
raise SystemExit(1)
#fragmentshader=gl.glCreateShader(gl.GL_FRAGMENT_SHADER)
#gl.glShaderSource(fragmentshader,1,fragment)
#gl.glCompileShader(fragmentshader)
try:
fragmentshader=shaders.compileShader(fragment, gl.GL_FRAGMENT_SHADER)
except RuntimeError as ex:
print ex[0]
raise SystemExit(1)
self.program=gl.glCreateProgram()
gl.glAttachShader(self.program,vertexshader)
gl.glAttachShader(self.program,fragmentshader)
gl.glLinkProgram(self.program)
self.uniforms={}
self.attributes=[]
self.initialised=True
def adduniform(self,name,glfunc):
self.uniforms[name]=(gl.glGetUniformLocation(self.program,name),glfunc)
def addattribute(self,name,count,attrpos,type_,normalized=False):
#self.attributes[name]=gl.glGetAttribLocation(self.program,name)
normalized=gl.GL_TRUE if normalized else gl.GL_FALSE
#attrpos=gl.glGetAttribLocation(self.program,name)
#print attrpos
gl.glEnableVertexAttribArray(attrpos)
gl.glVertexAttribPointer(attrpos,count,type_,normalized,0,None)
self.attributes.append(attrpos)
def setuniform(self,attr,value):
location,function=self.uniforms[name]
function(location,value)
def disuse(self):
for attribute in self.attributes:
gl.glDisableVertexAttribArray(attribute)
ShaderProgram.activeshader=None
def use(self):
for attribute in self.attributes:
gl.glEnableVertexAttribArray(attribute)
if ShaderProgram.activeshader!=None:
ShaderProgram.activeshader.disuse()
gl.glUseProgram(self.program)
ShaderProgram.activeshader=self
class Texture(object):
def __init__(self,image):
self.texture=gl.glGenTextures(1)
gl.glBindTexture(gl.GL_TEXTURE_2D,self.texture);
gl.glTexParameteri(gl.GL_TEXTURE_2D,gl.GL_TEXTURE_MIN_FILTER,gl.GL_LINEAR);
gl.glTexParameteri(gl.GL_TEXTURE_2D,gl.GL_TEXTURE_MAG_FILTER,gl.GL_LINEAR);
gl.glTexParameteri(gl.GL_TEXTURE_2D,gl.GL_TEXTURE_WRAP_S,gl.GL_CLAMP_TO_EDGE);
gl.glTexParameteri(gl.GL_TEXTURE_2D,gl.GL_TEXTURE_WRAP_T,gl.GL_CLAMP_TO_EDGE);
try:
data=image.tostring("raw", "RGBA", 0, -1)
except SystemError:
data=image.tostring("raw", "RGBX", 0, -1)
gl.glTexImage2D(gl.GL_TEXTURE_2D,0,gl.GL_RGBA,image.size[0],image.size[1],0,gl.GL_RGBA,gl.GL_UNSIGNED_BYTE,data)
class Mesh(object):
def __init__(self):
#target=gl.GL_ARRAY_BUFFER;
self.vertex_buffer=gl.glGenBuffers(1)
self.element_buffer=gl.glGenBuffers(1)
self.mode=gl.GL_DYNAMIC_DRAW
self.elementmode=gl.GL_TRIANGLES
self.elementcount=0
@property
def vertices(self):
raise AttributeError("write-only attribute")
@vertices.setter
def vertices(self,v):
gl.glBindBuffer(gl.GL_ARRAY_BUFFER,self.vertex_buffer)
gl.glBufferData(gl.GL_ARRAY_BUFFER,len(v),np.array(v),self.mode)
@property
def elements(self):
raise AttributeError("write-only attribute")
@elements.setter
def elements(self,v):
self.elementcount=len(v)
gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER,self.element_buffer)
gl.glBufferData(gl.GL_ELEMENT_ARRAY_BUFFER,len(v),np.array(v),self.mode)
def render(self):
gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER,self.element_buffer)
gl.glDrawElements(self.elementmode,self.elementcount,gl.GL_UNSIGNED_INT,None)
class Engine(object):
eventmapping={
sdl2.SDL_KEYDOWN:"on_keydown",
sdl2.SDL_KEYUP:"on_keyup",
sdl2.SDL_MOUSEMOTION:"on_mousemotion",
sdl2.SDL_MOUSEBUTTONUP:"on_mousebuttonup",
sdl2.SDL_MOUSEBUTTONDOWN:"on_mousebuttondown",
sdl2.SDL_MOUSEWHEEL:"on_mousewheel",
sdl2.SDL_QUIT:"on_quit",
sdl2.SDL_WINDOWEVENT:"on_window"
}
def __init__(self,size):
sdl2.SDL_Init(sdl2.SDL_INIT_VIDEO)
sdl2.SDL_GL_SetAttribute(sdl2.SDL_GL_CONTEXT_MAJOR_VERSION,3)
sdl2.SDL_GL_SetAttribute(sdl2.SDL_GL_CONTEXT_MINOR_VERSION,2)
sdl2.SDL_GL_SetAttribute(sdl2.SDL_GL_DOUBLEBUFFER,1)
sdl2.SDL_GL_SetAttribute(sdl2.SDL_GL_DEPTH_SIZE,24)
sdl2.SDL_GL_SetSwapInterval(0)
W,H=size
self.window=sdl2.SDL_CreateWindow("OpenGL Game",sdl2.SDL_WINDOWPOS_UNDEFINED,sdl2.SDL_WINDOWPOS_UNDEFINED,W,H,sdl2.SDL_WINDOW_OPENGL|sdl2.SDL_WINDOW_SHOWN)
#self.renderer=sdl2.SDL_CreateRenderer(self.window,-1,0)
self.glcontext=sdl2.SDL_GL_CreateContext(self.window)
sdl2.SDL_GL_MakeCurrent(self.window,self.glcontext)
self.frametime=1/30
self.pframe=None
def quit():
sdl2.SDL_GL_DeleteContext(self.glcontext)
sdl2.SDL_DestroyWindow(self.window)
sdl2.SDL_Quit()
atexit.register(quit)
def on_quit(self,event):
raise SystemExit()
def run(self):
quit=False
while not quit:
for event in sdl2.ext.get_events():
if event.type in self.eventmapping:
f=self.eventmapping[event.type]
if hasattr(self,f):
getattr(self,f)(event)
else:
print "unsupported event type",event.type
self.render()
if self.pframe!=None:
time_passed=sdl2.SDL_GetTicks()-self.pframe
if(time_passed<self.frametime):
sdl2.SDL_Delay(int((self.frametime-time_passed)*1000))
self.pframe=sdl2.SDL_GetTicks()
def render(self):
gl.glClearColor(0.5,0.5,0.5,1)
gl.glClear(gl.GL_COLOR_BUFFER_BIT)
sdl2.SDL_GL_SwapWindow(self.window)
class TestEngine(Engine):
def render(self):
gl.glClearColor(0.5,0.5,0.5,1)
gl.glClear(gl.GL_COLOR_BUFFER_BIT)
self.mesh.render()
sdl2.SDL_GL_SwapWindow(self.window)
e=TestEngine((800,600))
m=Mesh()
m.elementmode=gl.GL_TRIANGLE_FAN
m.vertices=[-1,-1,
1,-1,
-1, 1,
1, 1]
m.elements=[0,1,2,3]
e.mesh=m
t=Texture(Image.open("textures/test.png"))
s=ShaderProgram("shaders/test")
s.addattribute("position",2,0,gl.GL_FLOAT)
s.use()
e.run()
#version 330 core
layout(location=0) in vec2 position;
out vec2 pos;
void main()
{
gl_Position.xy=pos;
gl_Position.z=1.0;
gl_Position.w=1.0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment