python – PyOpenGL如何使用glGenBuffers实现它的神奇功能?

前端之家收集整理的这篇文章主要介绍了python – PyOpenGL如何使用glGenBuffers实现它的神奇功能?前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。

我试图回避PyOpenGL的缓慢且高开销的后端前端,并特别使用原始后端实现……

我遇到的问题是我似乎无法弄清楚前端如何将后端函数glGenBuffers(n,buffers)转换为buffers = glGenBuffers(n).

我想知道的是我将什么传递给后端函数的buffers参数?

最佳答案
以下是使用glGenBuffers创建一个或多个缓冲区的一些示例.如果必须使用像glGenBuffers(n,buffers)这样的函数调用,可以直接使用ctypes,也可以使用PyOpenGL的GLint,它包含了一个ctypes数据类型.

import ctypes
import numpy as np
from OpenGL.GL import *
import pygame

pygame.init()
screen = pygame.display.set_mode((800,600),pygame.OPENGL | pygame.DOUBLEBUF) #initialize OpenGL

py_id = glGenBuffers(1) #typical way to generate a single index
c_id = ctypes.c_int() #using ctypes to generate a second index
glGenBuffers(1,c_id)
gl_id = GLint() #using GL wrapper to generate a third index
glGenBuffers(1,gl_id)
print py_id,c_id.value,gl_id.value #should print 1 2 3

n = 10
py_list = glGenBuffers(n) #typical way to generate multiple indices
c_list = (ctypes.c_int * n)() #using ctypes to generate multiple indices
glGenBuffers(n,c_list)
gl_list = (GLint * n)() #using GL wrapper to generate multiple indices
glGenBuffers(n,gl_list)
print py_list,list(py_list) #note the default is a numpy array!
print np.array(c_list),list(c_list)
print np.array(gl_list),list(gl_list)

作为旁注,我不确定这样做的好处是什么.我怀疑glGenBuffers周围的方便包装器真的很慢,应该避免使用像buffers = glGenBuffers(n)这样的典型方法.我真的很想知道这是否是您的性能瓶颈.希望这可以帮助!

更新:
在你对__call__的开销进行评论后,我想我会在timeit中测试它.这是我的代码,每个定时块旁边的结果以秒为单位:

import ctypes
import numpy as np
from OpenGL.GL import *
import pygame
import timeit

pygame.init()
screen = pygame.display.set_mode((800,pygame.OPENGL | pygame.DOUBLEBUF) #initialize OpenGL

def test(func,repeats):
    start_time = timeit.default_timer()
    for i in range(repeats):
        func()
    elapsed = timeit.default_timer() - start_time
    print elapsed

def func1():
    py_id = glGenBuffers(1)

def func2():
    c_id = ctypes.c_int()
    glGenBuffers(1,c_id)

def func3():
    gl_id = GLint()
    glGenBuffers(1,gl_id)

def func4():
    n = 1
    py_list = glGenBuffers(n)

def func5():
    n = 1
    c_list = (ctypes.c_int * n)()
    glGenBuffers(n,c_list)

def func6():
    n = 1
    gl_list = (GLint * n)()
    glGenBuffers(n,gl_list)

def func7():
    n = 100
    py_list = glGenBuffers(n)

def func8():
    n = 100
    c_list = (ctypes.c_int * n)()
    glGenBuffers(n,c_list)

def func9():
    n = 100
    gl_list = (GLint * n)()
    glGenBuffers(n,gl_list)

test(func1,1000000)#4.12597930903
test(func2,1000000)#5.2951610055
test(func3,1000000)#5.17853478658
test(func4,1000000)#4.06362866711
test(func5,1000000)#3.45259988251
test(func6,1000000)#3.43240155354
test(func7,1000000)#4.128162421
test(func8,1000000)#3.57384911559
test(func9,1000000)#3.52125689729

从这些结果看,您生成的缓冲区数量似乎不会产生太大影响,因此即使n = 1,也应始终将其视为列表.不确定为什么会这样,也许在这种情况下会在幕后进行某种转换.奇怪的是,看起来GLint()的表现比直接使用ctypes要好,这对我来说也没有意义.无论哪种方式,纯python版本执行速度最慢,我想,对于其他更复杂的OpenGL函数,差异可能更大!

猜你在找的Python相关文章