Created
May 27, 2017 16:25
-
-
Save devilholk/bd9cffca7e250e27a4e440bd3830b2a0 to your computer and use it in GitHub Desktop.
Simple free fly camera (libglfw, libGL, python3)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from lowlevel_gl import * | |
# Test | |
#Kom ihåg error check för push/pop matrix | |
import threading | |
assert glfwInit() == 1 | |
w = glfwCreateWindow(640, 480, b"Hello World!", None, None) | |
assert w, 'Failed to create window' | |
sx = 100 | |
sy = 100 | |
sr = 45 | |
s = 100 | |
fov = 90 | |
class identity_matrix(matrix_f): | |
def __init__(self): | |
matrix_f.__init__(self) | |
self[0][0] = 1.0 | |
self[1][1] = 1.0 | |
self[2][2] = 1.0 | |
self[3][3] = 1.0 | |
#camera_pos = vec3(0,100,-500) | |
class camera: | |
def __init__(self, initial_position): | |
self.position = initial_position | |
self.id = identity_matrix() | |
self.up = vec_3f(0,1,0) | |
self.tilt = 0.0 | |
self.pan = 0.0 | |
self.motion = vec_3f() | |
self.local = identity_matrix() | |
def think(self): | |
i = self.local.invert() | |
#self.position += vec_3f(*(self.local.z * self.motion.z * -5.0)[:3]) | |
self.position += vec_3f(*(i.z * self.motion.z * 5.0)[:3]) | |
self.position += vec_3f(*(i.x * self.motion.x * 5.0)[:3]) | |
def mouse_xy(self, dx, dy): | |
self.pan = -.1 * dx | |
self.tilt = .1 * dy | |
def apply_transform(self): | |
self.local = matrix_f.rodriguez_transform(self.up, self.pan) * matrix_f.rodriguez_transform(self.id.x, self.tilt) | |
glMultMatrixf(self.local) | |
glTranslatef(*self.position) | |
cam = camera(vec_3f(0, 100, -500)) | |
def render_test_loop(window): | |
global cam | |
glfwMakeContextCurrent(window) | |
width = ctypes.c_int(0) | |
height = ctypes.c_int(0) | |
#glBlendFunc(GL_SRC_ALPHA, GL_ONE); | |
glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_SRC_ALPHA); | |
glEnable(GL_BLEND) | |
while not glfwWindowShouldClose(window): | |
rx = math.sin(time.time())*30+30 | |
ry = math.cos(time.time())*30+30 | |
cam.think() | |
glfwGetFramebufferSize(window, int_pointer(width), int_pointer(height)) | |
glViewport(0,0, width.value-1, height.value-1) | |
#glMatrixMode(GL_PROJECTION) | |
#glLoadIdentity() | |
#glOrtho(0, width.value-1, height.value-1, 0,0,1) | |
gl_perspective(fov, width.value/height.value, 1, 20000) | |
cam.apply_transform() | |
glMatrixMode(GL_MODELVIEW) | |
glLoadIdentity() | |
glClear(GL_COLOR_BUFFER_BIT) | |
q = 50 | |
glPushMatrix() | |
glTranslatef(-q*s/2,0,-q*s/2) | |
glColor4f(0.7,1.0,0.3,0.4) | |
glBegin(GL_LINES) | |
for c in range(q+1): | |
glVertex3f(c*s, 0, 0) | |
glVertex3f(c*s, 0, q*s) | |
glVertex3f(0, 0, c*s) | |
glVertex3f(q*s, 0, c*s) | |
glEnd() | |
glPopMatrix() | |
glfwSwapBuffers(window) | |
glfwPollEvents() | |
glfwDestroyWindow(window) | |
glfwTerminate() | |
t = threading.Thread(target=render_test_loop, args=(w,)) | |
t.start() | |
camera_control = None | |
last_pos = None | |
def handle_key(window, key, scancode, action, mods): | |
global camera_control, last_pos, cam | |
if key == 32: | |
if action == GLFW_PRESS.value: | |
if camera_control: | |
camera_control = None | |
else: | |
camera_control = cam | |
if camera_control: | |
last_pos = None | |
glfwSetInputMode(w, GLFW_CURSOR, GLFW_CURSOR_DISABLED) | |
else: | |
glfwSetInputMode(w, GLFW_CURSOR, GLFW_CURSOR_NORMAL) | |
return | |
if key == 256: | |
glfwSetWindowShouldClose(w, GLFW_TRUE) | |
return | |
if camera_control: | |
if key == ord('W'): | |
if action == GLFW_PRESS.value: | |
camera_control.motion.z = 1.0 | |
elif action == GLFW_RELEASE.value: | |
camera_control.motion.z = 0.0 | |
return | |
if key == ord('S'): | |
if action == GLFW_PRESS.value: | |
camera_control.motion.z = -1.0 | |
elif action == GLFW_RELEASE.value: | |
camera_control.motion.z = 0.0 | |
return | |
if key == ord('A'): | |
if action == GLFW_PRESS.value: | |
camera_control.motion.x = 1.0 | |
elif action == GLFW_RELEASE.value: | |
camera_control.motion.x = 0.0 | |
return | |
if key == ord('D'): | |
if action == GLFW_PRESS.value: | |
camera_control.motion.x = -1.0 | |
elif action == GLFW_RELEASE.value: | |
camera_control.motion.x = 0.0 | |
return | |
print("unhandled key", window, key, scancode, action, mods) | |
def handle_cursor(window, x, y): | |
global last_pos, camera_matrix, old_camera_matrix | |
if camera_control: | |
if last_pos != None: | |
ox, oy = last_pos | |
camera_control.mouse_xy(x - ox, y - oy) | |
else: | |
last_pos = x, y | |
cb1 = cursor_callback_signature(handle_cursor) | |
cb2 = key_callback_signature(handle_key) | |
glfwSetCursorPosCallback(w, cb1) | |
glfwSetKeyCallback(w, cb2) | |
print(cb1, cb2) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment